Boss sheet
This commit is contained in:
parent
d1d8bb8516
commit
31f29772f1
12
hench.mjs
12
hench.mjs
@ -1,4 +1,4 @@
|
|||||||
import { HenchDataModel } from "./module/data-models.mjs";
|
import { BossDataModel, HenchDataModel } from "./module/data-models.mjs";
|
||||||
|
|
||||||
import { HenchActorSheet } from "./module/sheets/hench-actor-sheet.mjs";
|
import { HenchActorSheet } from "./module/sheets/hench-actor-sheet.mjs";
|
||||||
|
|
||||||
@ -8,6 +8,15 @@ Handlebars.registerHelper('int2checkbox', (size, threshold, options) => {
|
|||||||
).reduce((prev, next) => (prev + next), "");
|
).reduce((prev, next) => (prev + next), "");
|
||||||
});
|
});
|
||||||
|
|
||||||
|
Handlebars.registerHelper('partialint2checkbox', (size, threshold, start, end, options) => {
|
||||||
|
const indexBase = start + 1;
|
||||||
|
const arrSize = Math.max(end - start, 0);
|
||||||
|
|
||||||
|
return Array(arrSize).fill(0).map(
|
||||||
|
(e, i) => options.fn({ index: i + indexBase, marked: (i + start) < threshold })
|
||||||
|
).reduce((prev, next) => (prev + next), "");
|
||||||
|
});
|
||||||
|
|
||||||
Handlebars.registerHelper('partialList', (list, start, end, options) => {
|
Handlebars.registerHelper('partialList', (list, start, end, options) => {
|
||||||
return list.slice(start, end).map(
|
return list.slice(start, end).map(
|
||||||
(e, i) => options.fn({ item: e, index: (start + i)})
|
(e, i) => options.fn({ item: e, index: (start + i)})
|
||||||
@ -28,6 +37,7 @@ Handlebars.registerHelper('decrement', (value) => (value - 1));
|
|||||||
Hooks.once("init", () => {
|
Hooks.once("init", () => {
|
||||||
CONFIG.Actor.dataModels = {
|
CONFIG.Actor.dataModels = {
|
||||||
hench: HenchDataModel,
|
hench: HenchDataModel,
|
||||||
|
boss: BossDataModel,
|
||||||
};
|
};
|
||||||
|
|
||||||
Actors.unregisterSheet('core', ActorSheet);
|
Actors.unregisterSheet('core', ActorSheet);
|
||||||
|
142
module/boss.mjs
Normal file
142
module/boss.mjs
Normal file
@ -0,0 +1,142 @@
|
|||||||
|
export const nullStorylineKey = "FREEFORM";
|
||||||
|
|
||||||
|
export const storylineKeys = [
|
||||||
|
nullStorylineKey,
|
||||||
|
"BOOTSTRAPPER",
|
||||||
|
"VENGEANCE",
|
||||||
|
"DOWNWARD SPIRAL",
|
||||||
|
"DOMINION",
|
||||||
|
"CLEANUP CREW"
|
||||||
|
];
|
||||||
|
|
||||||
|
export function getBossMutation() {
|
||||||
|
return bossData;
|
||||||
|
}
|
||||||
|
|
||||||
|
const bossData = {
|
||||||
|
details: [
|
||||||
|
{
|
||||||
|
question: "What fuels your quest for villainy?",
|
||||||
|
answer: "",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
question: "How do you dress your henches?",
|
||||||
|
answer: "",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
question: "How is your lair designed? ",
|
||||||
|
answer: "",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
question: "Where do you draw the line to what you will do? ",
|
||||||
|
answer: "",
|
||||||
|
},
|
||||||
|
],
|
||||||
|
moves: [
|
||||||
|
{
|
||||||
|
marked: true,
|
||||||
|
name: "Force of Will",
|
||||||
|
description: `Whenever you act, do not draw. Simply declare what you do, and what happens after.`,
|
||||||
|
hasWriteIn: false,
|
||||||
|
writeIn: null,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
marked: false,
|
||||||
|
name: "Extra Armorment",
|
||||||
|
description: `Write in an additional gear type on each of your henches' sheets. They can take it on any future mission.`,
|
||||||
|
hasWriteIn: false,
|
||||||
|
writeIn: null,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
marked: false,
|
||||||
|
name: "Rotating Armorment I",
|
||||||
|
description: `Erase the write-in gear from any number of your henches' sheets, and write in a new equipment.`,
|
||||||
|
hasWriteIn: false,
|
||||||
|
writeIn: null,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
marked: false,
|
||||||
|
name: "Rotating Armorment II",
|
||||||
|
description: `Erase the write-in gear from any number of your henches' sheets, and write in a new equipment.`,
|
||||||
|
hasWriteIn: false,
|
||||||
|
writeIn: null,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
marked: false,
|
||||||
|
name: "Rotating Armorment III",
|
||||||
|
description: `Erase the write-in gear from any number of your henches' sheets, and write in a new equipment.`,
|
||||||
|
hasWriteIn: false,
|
||||||
|
writeIn: null,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
marked: false,
|
||||||
|
name: "Specialized Training",
|
||||||
|
description: `Write a new inclination below. It applies for all of your henches.`,
|
||||||
|
hasWriteIn: true,
|
||||||
|
writeIn: "",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
marked: false,
|
||||||
|
name: "General Training",
|
||||||
|
description: `When you take this ability, fill the experience track of each of your henches immediately.`,
|
||||||
|
hasWriteIn: false,
|
||||||
|
writeIn: null,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
marked: false,
|
||||||
|
name: "Exceptional Planning",
|
||||||
|
description: `At the start of each mission, remove one card from the deck. Any time one of your henches draws, you may replace the card they play with the removed card.`,
|
||||||
|
hasWriteIn: false,
|
||||||
|
writeIn: null,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
marked: false,
|
||||||
|
name: "Limelight Lovers",
|
||||||
|
description: `If your heat is in Tier III, your henches can take 1 stress to take +1 card to any draw <em>(possibly drawing 4)</em>.`,
|
||||||
|
hasWriteIn: false,
|
||||||
|
writeIn: null,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
marked: false,
|
||||||
|
name: "Plot Armor",
|
||||||
|
description: `Once per mission, one of your henches can ignore any single instance of harm they would take.`,
|
||||||
|
hasWriteIn: false,
|
||||||
|
writeIn: null,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
marked: false,
|
||||||
|
name: "Play it Off",
|
||||||
|
description: `Your henches can resist consequences by taking 1 harm "Laughing Stock", instead of marking stress. They can do this even if all of their stress is marked.`,
|
||||||
|
hasWriteIn: false,
|
||||||
|
writeIn: null,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
marked: false,
|
||||||
|
name: "Guild Bigwig",
|
||||||
|
description: `During fallout, you may draw a second time and use that card instead. Explain who intervenes on your behalf, and how.`,
|
||||||
|
hasWriteIn: false,
|
||||||
|
writeIn: null,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
marked: false,
|
||||||
|
name: "Exit Plan",
|
||||||
|
description: `When you take this move, pick a hench to pass the mantle on to. You retire to peace, and they take your place. Is there any ceremony to the transfer? Who knows, and who doesn't?`,
|
||||||
|
hasWriteIn: false,
|
||||||
|
writeIn: null,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
experienceTriggers: [
|
||||||
|
{
|
||||||
|
marked: false,
|
||||||
|
description: "Your henches followed even your most superfluous orders.",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
marked: false,
|
||||||
|
description: "You achieved your evil ambitions.",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
marked: false,
|
||||||
|
description: "News of your deeds spreads far and wide.",
|
||||||
|
},
|
||||||
|
]
|
||||||
|
};
|
@ -1,5 +1,6 @@
|
|||||||
const { HTMLField, SchemaField, NumberField, StringField, BooleanField, FilePathField, ArrayField } = foundry.data.fields;
|
const { HTMLField, SchemaField, NumberField, StringField, BooleanField, FilePathField, ArrayField } = foundry.data.fields;
|
||||||
|
|
||||||
|
import { getBossMutation, nullStorylineKey, storylineKeys } from './boss.mjs';
|
||||||
import { nullPlaybookKey, playbookKeys, lookupPlaybook, getPlaybookMutation } from './playbooks.mjs';
|
import { nullPlaybookKey, playbookKeys, lookupPlaybook, getPlaybookMutation } from './playbooks.mjs';
|
||||||
|
|
||||||
const textField = () => new StringField({ required: true, blank: true });
|
const textField = () => new StringField({ required: true, blank: true });
|
||||||
@ -110,4 +111,42 @@ export class HenchDataModel extends foundry.abstract.TypeDataModel {
|
|||||||
this.customGear,
|
this.customGear,
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export class BossDataModel extends foundry.abstract.TypeDataModel {
|
||||||
|
static defineSchema() {
|
||||||
|
return {
|
||||||
|
look: textField(),
|
||||||
|
details: cappedArrayField(promptField(), 4),
|
||||||
|
storyline: new StringField({ required: true, blank: false, initial: nullStorylineKey, options: storylineKeys}),
|
||||||
|
|
||||||
|
heat: new NumberField({ required: true, integer: true, min: 0, initial: 0, max: 18}),
|
||||||
|
|
||||||
|
experienceTriggers: cappedArrayField(markableField(), 4),
|
||||||
|
experience: new NumberField({ required: true, integer: true, min: 0, initial: 0, max: 5 }),
|
||||||
|
|
||||||
|
moves: cappedArrayField(moveField(), 13),
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
static migrateData(source) {
|
||||||
|
// no migrations yet
|
||||||
|
|
||||||
|
return super.migrateData(source);
|
||||||
|
}
|
||||||
|
|
||||||
|
/** @override */
|
||||||
|
async _preCreate(data, options, user) {
|
||||||
|
await super._preCreate(data, options, user);
|
||||||
|
|
||||||
|
const initMutation = getBossMutation();
|
||||||
|
|
||||||
|
return this.updateSource(initMutation);
|
||||||
|
}
|
||||||
|
|
||||||
|
get tier() {
|
||||||
|
const divisor = 18 / 3;
|
||||||
|
|
||||||
|
return Math.ceil(this.heat / divisor);
|
||||||
|
}
|
||||||
}
|
}
|
@ -1,5 +1,6 @@
|
|||||||
import { playbookKeys, validatePlaybookKey, getPlaybookMutation } from "../playbooks.mjs";
|
import { playbookKeys, validatePlaybookKey, getPlaybookMutation } from "../playbooks.mjs";
|
||||||
import { updateField } from "../helpers/mutation-helper.mjs";
|
import { updateField } from "../helpers/mutation-helper.mjs";
|
||||||
|
import { storylineKeys } from "../boss.mjs";
|
||||||
|
|
||||||
export class HenchActorSheet extends ActorSheet {
|
export class HenchActorSheet extends ActorSheet {
|
||||||
/** @override */
|
/** @override */
|
||||||
@ -13,10 +14,12 @@ export class HenchActorSheet extends ActorSheet {
|
|||||||
const context = super.getData();
|
const context = super.getData();
|
||||||
|
|
||||||
context.playbookKeys = playbookKeys.map((k) => ({ key: k, selected: k === this.actor.system.playbook}));
|
context.playbookKeys = playbookKeys.map((k) => ({ key: k, selected: k === this.actor.system.playbook}));
|
||||||
|
context.storylineKeys = storylineKeys.map((k) => ({ key: k, selected: k === this.actor.system.storyline}));
|
||||||
|
|
||||||
// TODO define system constants for these
|
// TODO define system constants for these
|
||||||
context.maxStress = 12;
|
context.maxStress = 12;
|
||||||
context.maxExp = 5;
|
context.maxExp = 5;
|
||||||
|
context.maxHeat = 18;
|
||||||
|
|
||||||
context.minGear = 3;
|
context.minGear = 3;
|
||||||
context.maxGear = 5;
|
context.maxGear = 5;
|
||||||
@ -54,6 +57,14 @@ export class HenchActorSheet extends ActorSheet {
|
|||||||
updateField(this.actor, path, value);
|
updateField(this.actor, path, value);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// normal dropdowns
|
||||||
|
html.find('.hench-hench-sheet-dropdown').on('change', (event) => {
|
||||||
|
const value = event.target.value;
|
||||||
|
const path = event.currentTarget.dataset.fieldPath;
|
||||||
|
|
||||||
|
updateField(this.actor, path, value);
|
||||||
|
});
|
||||||
|
|
||||||
// text fields
|
// text fields
|
||||||
html.find('.hench-text-input').on('change', async (event) => {
|
html.find('.hench-text-input').on('change', async (event) => {
|
||||||
const element = event.currentTarget;
|
const element = event.currentTarget;
|
||||||
|
@ -48,6 +48,11 @@
|
|||||||
font-size: 1.5em;
|
font-size: 1.5em;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.hench-huge {
|
||||||
|
font-size: 3em;
|
||||||
|
font-weight: 700;
|
||||||
|
}
|
||||||
|
|
||||||
/* Flexbox */
|
/* Flexbox */
|
||||||
.hench-row {
|
.hench-row {
|
||||||
display: flex;
|
display: flex;
|
||||||
|
169
templates/actors/boss.hbs
Normal file
169
templates/actors/boss.hbs
Normal file
@ -0,0 +1,169 @@
|
|||||||
|
<form>
|
||||||
|
<div class="hench-sheet-container hench-padding-wide hench-gap-wide hench-white">
|
||||||
|
<!-- ID row -->
|
||||||
|
<div class="hench-row hench-gap-wide">
|
||||||
|
<!-- core-->
|
||||||
|
<div class="hench-box hench-flex-resizeable hench-l-grey hench-padding-wide hench-gap-narrow">
|
||||||
|
<!-- Name -->
|
||||||
|
<div class="hench-field hench-row hench-gap-narrow">
|
||||||
|
<label class="hench-flex-fixed" for="hench-name">Name: </label>
|
||||||
|
<input type="text" name="hench-name" class="hench-text-input hench-flex-resizeable" value="{{actor.name}}" data-field-path="name" />
|
||||||
|
</div>
|
||||||
|
<!-- Look -->
|
||||||
|
<div class="hench-field hench-row hench-gap-narrow">
|
||||||
|
<label class="hench-flex-fixed" for="hench-look">Look: </label>
|
||||||
|
<input type="text" name="hench-look" class="hench-text-input hench-flex-resizeable" value="{{actor.system.look}}" data-field-path="system.look" />
|
||||||
|
</div>
|
||||||
|
<!-- Storyline -->
|
||||||
|
<div class="hench-field hench-row hench-gap-narrow">
|
||||||
|
<label class="hench-flex-fixed" for="hench-storyline">Storyline: </label>
|
||||||
|
<select name="hench-storyline" class="hench-hench-sheet-dropdown hench-flex-resizeable" data-field-path="system.storyline">
|
||||||
|
{{#each storylineKeys}}
|
||||||
|
<option value="{{this.key}}" {{#if this.selected}}selected{{/if}}>{{this.key}}</option>
|
||||||
|
{{/each}}
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="hench-box hench-d-grey hench-flex-resizeable hench-centered hench-huge">
|
||||||
|
THE BOSS
|
||||||
|
</div>
|
||||||
|
<!-- icon -->
|
||||||
|
<div class="hench-box hench-l-grey hench-flex-fixed">
|
||||||
|
<img src="{{actor.img}}" data-edit="img" class="hench-icon" />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<!-- Big Box -->
|
||||||
|
<div class="hench-row hench-gap-wide">
|
||||||
|
<!-- Column -->
|
||||||
|
<div class="hench-box hench-box-stretch hench-flex-fixed hench-gap-wide">
|
||||||
|
<!-- Details -->
|
||||||
|
<div class="hench-row hench-flex-resizeable">
|
||||||
|
<div class="hench-box hench-l-grey hench-flex-resizeable hench-padding-wide hench-gap-narrow">
|
||||||
|
<div class="hench-row hench-flex-resizeable">
|
||||||
|
<div class="hench-centered hench-title hench-flex-resizeable">
|
||||||
|
Details
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{{#each actor.system.details}}
|
||||||
|
<div class="hench-row">
|
||||||
|
<label for="hench-detail-{{@index}}">{{this.question}}</label>
|
||||||
|
</div>
|
||||||
|
<div class="hench-row">
|
||||||
|
<input name="hench-detail-{{@index}}" type="text" class="hench-text-input" data-field-path="system.details[{{@index}}].answer" value="{{this.answer}}" />
|
||||||
|
</div>
|
||||||
|
{{/each}}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<!-- Heat -->
|
||||||
|
<div class="hench-row hench-flex-resizeable">
|
||||||
|
<div class="hench-box hench-l-grey hench-flex-resizeable hench-padding-wide hench-gap-narrow">
|
||||||
|
<div class="hench-row hench-flex-resizeable">
|
||||||
|
<div class="hench-centered hench-title hench-flex-resizeable">
|
||||||
|
Heat
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="hench-row hench-centered hench-flex-resizeable">
|
||||||
|
<div class="hench-flex-resizeable hench-centered">
|
||||||
|
<strong>Tier I</strong>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="hench-row hench-centered hench-flex-resizeable">
|
||||||
|
<div class="hench-flex-resizeable hench-centered">
|
||||||
|
<em>(Nuisance, low-stakes, local cops)</em>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="hench-row hench-flex-resizeable hench-row-even hench-gap-narrow">
|
||||||
|
{{#partialint2checkbox maxHeat actor.system.heat 0 6}}
|
||||||
|
<input type="checkbox" class="hench-checkbox-int-field" data-field-path="system.heat" data-value="{{index}}" {{#if marked}} checked {{/if}} />
|
||||||
|
{{/partialint2checkbox}}
|
||||||
|
</div>
|
||||||
|
<div class="hench-row hench-centered hench-flex-resizeable">
|
||||||
|
<div class="hench-flex-resizeable hench-centered">
|
||||||
|
<strong>Tier II</strong>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="hench-row hench-centered hench-flex-resizeable">
|
||||||
|
<div class="hench-flex-resizeable hench-centered">
|
||||||
|
<em>(Full-time, classic stakes, local super)</em>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="hench-row hench-flex-resizeable hench-row-even hench-gap-narrow">
|
||||||
|
{{#partialint2checkbox maxHeat actor.system.heat 6 12}}
|
||||||
|
<input type="checkbox" class="hench-checkbox-int-field" data-field-path="system.heat" data-value="{{index}}" {{#if marked}} checked {{/if}} />
|
||||||
|
{{/partialint2checkbox}}
|
||||||
|
</div>
|
||||||
|
<div class="hench-row hench-centered hench-flex-resizeable">
|
||||||
|
<div class="hench-flex-resizeable hench-centered">
|
||||||
|
<strong>Tier III</strong>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="hench-row hench-centered hench-flex-resizeable">
|
||||||
|
<div class="hench-flex-resizeable hench-centered">
|
||||||
|
<em>(Top-class, high-stakes, world's finest heroes)</em>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="hench-row hench-flex-resizeable hench-row-even hench-gap-narrow">
|
||||||
|
{{#partialint2checkbox maxHeat actor.system.heat 12 18}}
|
||||||
|
<input type="checkbox" class="hench-checkbox-int-field" data-field-path="system.heat" data-value="{{index}}" {{#if marked}} checked {{/if}} />
|
||||||
|
{{/partialint2checkbox}}
|
||||||
|
</div>
|
||||||
|
<!-- maybe add guidelines down here? -->
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<!-- Experience -->
|
||||||
|
<div class="hench-row hench-flex-resizeable">
|
||||||
|
<div class="hench-box hench-l-grey hench-flex-resizeable hench-padding-narrow hench-gap-narrow">
|
||||||
|
<div class="hench-row hench-flex-resizeable">
|
||||||
|
<div class="hench-centered hench-title hench-flex-resizeable">
|
||||||
|
Experience
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="hench-row hench-row-even hench-gap-narrow hench-flex-resizeable">
|
||||||
|
{{#int2checkbox maxExp actor.system.experience}}
|
||||||
|
<input type="checkbox" class="hench-checkbox-int-field" data-field-path="system.experience" data-value="{{index}}" {{#if marked}} checked {{/if}} />
|
||||||
|
{{/int2checkbox}}
|
||||||
|
</div>
|
||||||
|
{{#each actor.system.experienceTriggers}}
|
||||||
|
<div class="hench-row hench-m-grey hench-flex-resizeable hench-padding-narrow hench-gap-narrow">
|
||||||
|
<div class="hench-box hench-flex-fixed">
|
||||||
|
<input type="checkbox" class="hench-checkbox hench-checkbox-toggle-field" data-field-path="system.experienceTriggers[{{@index}}].marked" {{#if this.marked}} checked {{/if}} />
|
||||||
|
</div>
|
||||||
|
<div class="hench-box hench-flex-resizeable">
|
||||||
|
{{this.description}}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{{/each}}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<!-- Moves -->
|
||||||
|
<div class="hench-box hench-flex-resizeable hench-m-grey hench-padding-narrow hench-gap-narrow">
|
||||||
|
<div class="hench-row">
|
||||||
|
<div class="hench-centered hench-title hench-flex-resizeable">
|
||||||
|
Abilities
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{{#each actor.system.moves}}
|
||||||
|
<div class="hench-row hench-l-grey hench-flex-resizeable hench-gap-narrow">
|
||||||
|
<div class="hench-box hench-flex-fixed">
|
||||||
|
<input type="checkbox" name="hench-move-checkbox-{{@index}}" class="hench-checkbox-toggle-field" data-field-path="system.moves[{{@index}}].marked" {{#if this.marked}}checked{{/if}} />
|
||||||
|
</div>
|
||||||
|
<div class="hench-box hench-flex-resizeable hench-gap-narrow hench-padding-narrow">
|
||||||
|
<div>
|
||||||
|
<label for="hench-move-checkbox-{{@index}}"><em><strong>{{this.name}}</strong></em></label>
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
{{{this.description}}}
|
||||||
|
</div>
|
||||||
|
{{#if this.hasWriteIn}}
|
||||||
|
<div>
|
||||||
|
<input type="text" name="hench-move-writein-{{$index}}" class="hench-text-field" data-field-path="system.moves[{{@index}}].writein" value="{{this.writein}}" />
|
||||||
|
</div>
|
||||||
|
{{/if}}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{{/each}}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</form>
|
Loading…
x
Reference in New Issue
Block a user