RC-63 | Display skills in sheet
This commit is contained in:
parent
df35c00c5d
commit
1302d91469
9 changed files with 142 additions and 24 deletions
|
|
@ -80,6 +80,7 @@ export class CombinedHeroSheet extends GenericAppMixin(HandlebarsApplicationMixi
|
||||||
|
|
||||||
ctx = await HeroSkillsCardV1.prepareGear(ctx);
|
ctx = await HeroSkillsCardV1.prepareGear(ctx);
|
||||||
ctx = await HeroSkillsCardV1.prepareAmmo(ctx);
|
ctx = await HeroSkillsCardV1.prepareAmmo(ctx);
|
||||||
|
ctx = await HeroSkillsCardV1.prepareSkills(ctx);
|
||||||
|
|
||||||
Logger.debug(`Context:`, ctx);
|
Logger.debug(`Context:`, ctx);
|
||||||
return ctx;
|
return ctx;
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,5 @@
|
||||||
import { deleteItemFromElement, editItemFromElement } from "../utils.mjs";
|
import { deleteItemFromElement, editItemFromElement } from "../utils.mjs";
|
||||||
import { filePath } from "../../consts.mjs";
|
import { documentSorter, filePath } from "../../consts.mjs";
|
||||||
import { gameTerms } from "../../gameTerms.mjs";
|
import { gameTerms } from "../../gameTerms.mjs";
|
||||||
import { GenericAppMixin } from "../GenericApp.mjs";
|
import { GenericAppMixin } from "../GenericApp.mjs";
|
||||||
import { localizer } from "../../utils/Localizer.mjs";
|
import { localizer } from "../../utils/Localizer.mjs";
|
||||||
|
|
@ -52,7 +52,7 @@ export class HeroSkillsCardV1 extends GenericAppMixin(HandlebarsApplicationMixin
|
||||||
} = options;
|
} = options;
|
||||||
new ContextMenu(
|
new ContextMenu(
|
||||||
element,
|
element,
|
||||||
`[data-ctx-menu="gear"]`,
|
`[data-ctx-menu="gear"],[data-ctx-menu="skill"]`,
|
||||||
[
|
[
|
||||||
{
|
{
|
||||||
name: localizer(`RipCrypt.common.edit`),
|
name: localizer(`RipCrypt.common.edit`),
|
||||||
|
|
@ -81,6 +81,7 @@ export class HeroSkillsCardV1 extends GenericAppMixin(HandlebarsApplicationMixin
|
||||||
|
|
||||||
ctx = await HeroSkillsCardV1.prepareGear(ctx);
|
ctx = await HeroSkillsCardV1.prepareGear(ctx);
|
||||||
ctx = await HeroSkillsCardV1.prepareAmmo(ctx);
|
ctx = await HeroSkillsCardV1.prepareAmmo(ctx);
|
||||||
|
ctx = await HeroSkillsCardV1.prepareSkills(ctx);
|
||||||
|
|
||||||
Logger.debug(`Context:`, ctx);
|
Logger.debug(`Context:`, ctx);
|
||||||
return ctx;
|
return ctx;
|
||||||
|
|
@ -122,6 +123,48 @@ export class HeroSkillsCardV1 extends GenericAppMixin(HandlebarsApplicationMixin
|
||||||
ctx.ammo = 0;
|
ctx.ammo = 0;
|
||||||
return ctx;
|
return ctx;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
static async prepareSkills(ctx) {
|
||||||
|
ctx.skills = {};
|
||||||
|
const abilities = Object.values(gameTerms.Abilities);
|
||||||
|
const heroRank = ctx.actor.system.level.rank;
|
||||||
|
const embeddedSkills = ctx.actor.itemTypes.skill.sort(documentSorter);
|
||||||
|
|
||||||
|
for (let ability of abilities) {
|
||||||
|
const skills = [];
|
||||||
|
for (const skill of embeddedSkills) {
|
||||||
|
if (skill.system.ability !== ability) { continue };
|
||||||
|
skills.push({
|
||||||
|
uuid: skill.uuid,
|
||||||
|
name: skill.name,
|
||||||
|
use: skill.system.advances[heroRank],
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
// Thin Glim is grouped with full glim.
|
||||||
|
if (ability === gameTerms.Abilities.THINGLIM) {
|
||||||
|
ability = gameTerms.Abilities.GLIM;
|
||||||
|
};
|
||||||
|
|
||||||
|
ctx.skills[ability] ??= [];
|
||||||
|
ctx.skills[ability].push(...skills);
|
||||||
|
};
|
||||||
|
|
||||||
|
const limit = ctx.actor.system.limit.skills;
|
||||||
|
for (const ability of abilities) {
|
||||||
|
if (ctx.skills[ability] == null) { continue };
|
||||||
|
|
||||||
|
const length = ctx.skills[ability].length;
|
||||||
|
if (length >= limit) {
|
||||||
|
ctx.skills[ability] = ctx.skills[ability].slice(0, limit);
|
||||||
|
} else {
|
||||||
|
ctx.skills[ability] = ctx.skills[ability]
|
||||||
|
.concat(Array(limit - length).fill(null))
|
||||||
|
.slice(0, limit);
|
||||||
|
};
|
||||||
|
}
|
||||||
|
return ctx;
|
||||||
|
};
|
||||||
// #endregion
|
// #endregion
|
||||||
|
|
||||||
// #region Actions
|
// #region Actions
|
||||||
|
|
|
||||||
|
|
@ -1,8 +1,12 @@
|
||||||
|
// App imports
|
||||||
import { CombinedHeroSheet } from "./Apps/ActorSheets/CombinedHeroSheet.mjs";
|
import { CombinedHeroSheet } from "./Apps/ActorSheets/CombinedHeroSheet.mjs";
|
||||||
import { DicePool } from "./Apps/DicePool.mjs";
|
import { DicePool } from "./Apps/DicePool.mjs";
|
||||||
import { HeroSkillsCardV1 } from "./Apps/ActorSheets/HeroSkillsCardV1.mjs";
|
import { HeroSkillsCardV1 } from "./Apps/ActorSheets/HeroSkillsCardV1.mjs";
|
||||||
import { HeroSummaryCardV1 } from "./Apps/ActorSheets/HeroSummaryCardV1.mjs";
|
import { HeroSummaryCardV1 } from "./Apps/ActorSheets/HeroSummaryCardV1.mjs";
|
||||||
|
|
||||||
|
// Util imports
|
||||||
|
import { documentSorter } from "./consts.mjs";
|
||||||
|
|
||||||
const { deepFreeze } = foundry.utils;
|
const { deepFreeze } = foundry.utils;
|
||||||
|
|
||||||
Object.defineProperty(
|
Object.defineProperty(
|
||||||
|
|
@ -16,6 +20,9 @@ Object.defineProperty(
|
||||||
HeroSummaryCardV1,
|
HeroSummaryCardV1,
|
||||||
HeroSkillsCardV1,
|
HeroSkillsCardV1,
|
||||||
},
|
},
|
||||||
|
utils: {
|
||||||
|
documentSorter,
|
||||||
|
},
|
||||||
}),
|
}),
|
||||||
writable: false,
|
writable: false,
|
||||||
},
|
},
|
||||||
|
|
|
||||||
|
|
@ -5,3 +5,13 @@ export function filePath(path) {
|
||||||
};
|
};
|
||||||
return `systems/ripcrypt/${path}`;
|
return `systems/ripcrypt/${path}`;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// MARK: documentSorter
|
||||||
|
export function documentSorter(a, b) {
|
||||||
|
const sortDelta = b.sort - a.sort;
|
||||||
|
if (sortDelta !== 0) {
|
||||||
|
return sortDelta;
|
||||||
|
};
|
||||||
|
// TODO alphabetical sort
|
||||||
|
return 0;
|
||||||
|
};
|
||||||
|
|
|
||||||
|
|
@ -132,6 +132,7 @@ export class HeroData extends foundry.abstract.TypeDataModel {
|
||||||
this.limit = {
|
this.limit = {
|
||||||
weapons: 4,
|
weapons: 4,
|
||||||
equipment: 12,
|
equipment: 12,
|
||||||
|
skills: 4,
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -2,19 +2,17 @@ import { gameTerms } from "../../gameTerms.mjs";
|
||||||
|
|
||||||
const { fields } = foundry.data;
|
const { fields } = foundry.data;
|
||||||
|
|
||||||
const abilityPaths = [`grit`, `gait`, `grip`, `glim`, `thin-glim`];
|
|
||||||
|
|
||||||
export class SkillData extends foundry.abstract.TypeDataModel {
|
export class SkillData extends foundry.abstract.TypeDataModel {
|
||||||
// MARK: Schema
|
// MARK: Schema
|
||||||
static defineSchema() {
|
static defineSchema() {
|
||||||
const schema = {
|
const schema = {
|
||||||
ability: new fields.StringField({
|
ability: new fields.StringField({
|
||||||
initial: abilityPaths[0],
|
initial: gameTerms.Abilities.GRIT,
|
||||||
blank: true,
|
blank: true,
|
||||||
trim: true,
|
trim: true,
|
||||||
nullable: false,
|
nullable: false,
|
||||||
required: true,
|
required: true,
|
||||||
choices: () => abilityPaths,
|
choices: () => Object.values(gameTerms.Abilities),
|
||||||
}),
|
}),
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
@ -53,7 +51,7 @@ export class SkillData extends foundry.abstract.TypeDataModel {
|
||||||
label: `RipCrypt.common.ability`,
|
label: `RipCrypt.common.ability`,
|
||||||
path: `system.ability`,
|
path: `system.ability`,
|
||||||
value: this.ability,
|
value: this.ability,
|
||||||
options: abilityPaths.map(ability => ({
|
options: Object.values(gameTerms.Abilities).map(ability => ({
|
||||||
label: `RipCrypt.common.abilities.${ability}`,
|
label: `RipCrypt.common.abilities.${ability}`,
|
||||||
value: ability,
|
value: ability,
|
||||||
})),
|
})),
|
||||||
|
|
|
||||||
|
|
@ -1,4 +1,11 @@
|
||||||
export const gameTerms = Object.preventExtensions({
|
export const gameTerms = Object.preventExtensions({
|
||||||
|
Abilities: Object.freeze({
|
||||||
|
GRIT: `grit`,
|
||||||
|
GRIP: `grip`,
|
||||||
|
GAIT: `gait`,
|
||||||
|
GLIM: `glim`,
|
||||||
|
THINGLIM: `thin-glim`,
|
||||||
|
}),
|
||||||
FatePath: [
|
FatePath: [
|
||||||
`North`,
|
`North`,
|
||||||
`East`,
|
`East`,
|
||||||
|
|
|
||||||
|
|
@ -4,10 +4,22 @@
|
||||||
<span class="small">{{ rc-i18n "RipCrypt.common.rank" }}</span>
|
<span class="small">{{ rc-i18n "RipCrypt.common.rank" }}</span>
|
||||||
</div>
|
</div>
|
||||||
<ol class="num-before skill-list even grit-skills">
|
<ol class="num-before skill-list even grit-skills">
|
||||||
<li></li>
|
{{#each skills.grit as | skill |}}
|
||||||
<li></li>
|
{{#if skill}}
|
||||||
<li></li>
|
<li data-item-id="{{skill.uuid}}" data-ctx-menu="skill">
|
||||||
<li></li>
|
<span class="name">{{ skill.name }}</span>
|
||||||
|
<rc-icon
|
||||||
|
name="icons/info-circle"
|
||||||
|
var:size="16px"
|
||||||
|
var:fill="currentColor"
|
||||||
|
data-tooltip="{{ skill.use }}"
|
||||||
|
data-tooltip-direction="UP"
|
||||||
|
></rc-icon>
|
||||||
|
</li>
|
||||||
|
{{else}}
|
||||||
|
<li></li>
|
||||||
|
{{/if}}
|
||||||
|
{{/each}}
|
||||||
</ol>
|
</ol>
|
||||||
|
|
||||||
<div class="label col-header list-header gait-skills-header">
|
<div class="label col-header list-header gait-skills-header">
|
||||||
|
|
@ -15,10 +27,22 @@
|
||||||
<span class="small">{{ rc-i18n "RipCrypt.common.rank" }}</span>
|
<span class="small">{{ rc-i18n "RipCrypt.common.rank" }}</span>
|
||||||
</div>
|
</div>
|
||||||
<ol class="num-before skill-list even gait-skills">
|
<ol class="num-before skill-list even gait-skills">
|
||||||
<li></li>
|
{{#each skills.gait as | skill |}}
|
||||||
<li></li>
|
{{#if skill}}
|
||||||
<li></li>
|
<li data-item-id="{{skill.uuid}}" data-ctx-menu="skill">
|
||||||
<li></li>
|
<span class="name">{{ skill.name }}</span>
|
||||||
|
<rc-icon
|
||||||
|
name="icons/info-circle"
|
||||||
|
var:size="16px"
|
||||||
|
var:fill="currentColor"
|
||||||
|
data-tooltip="{{ skill.use }}"
|
||||||
|
data-tooltip-direction="UP"
|
||||||
|
></rc-icon>
|
||||||
|
</li>
|
||||||
|
{{else}}
|
||||||
|
<li></li>
|
||||||
|
{{/if}}
|
||||||
|
{{/each}}
|
||||||
</ol>
|
</ol>
|
||||||
|
|
||||||
<div class="label col-header list-header grip-skills-header">
|
<div class="label col-header list-header grip-skills-header">
|
||||||
|
|
@ -26,10 +50,22 @@
|
||||||
<span class="small">{{ rc-i18n "RipCrypt.common.rank" }}</span>
|
<span class="small">{{ rc-i18n "RipCrypt.common.rank" }}</span>
|
||||||
</div>
|
</div>
|
||||||
<ol class="num-before skill-list odd grip-skills">
|
<ol class="num-before skill-list odd grip-skills">
|
||||||
<li></li>
|
{{#each skills.grip as | skill |}}
|
||||||
<li></li>
|
{{#if skill}}
|
||||||
<li></li>
|
<li data-item-id="{{skill.uuid}}" data-ctx-menu="skill">
|
||||||
<li></li>
|
<span class="name">{{ skill.name }}</span>
|
||||||
|
<rc-icon
|
||||||
|
name="icons/info-circle"
|
||||||
|
var:size="16px"
|
||||||
|
var:fill="currentColor"
|
||||||
|
data-tooltip="{{ skill.use }}"
|
||||||
|
data-tooltip-direction="UP"
|
||||||
|
></rc-icon>
|
||||||
|
</li>
|
||||||
|
{{else}}
|
||||||
|
<li></li>
|
||||||
|
{{/if}}
|
||||||
|
{{/each}}
|
||||||
</ol>
|
</ol>
|
||||||
|
|
||||||
<div class="label col-header list-header glim-skills-header">
|
<div class="label col-header list-header glim-skills-header">
|
||||||
|
|
@ -37,10 +73,22 @@
|
||||||
<span class="small">{{ rc-i18n "RipCrypt.common.rank" }}</span>
|
<span class="small">{{ rc-i18n "RipCrypt.common.rank" }}</span>
|
||||||
</div>
|
</div>
|
||||||
<ol class="num-before skill-list odd glim-skills">
|
<ol class="num-before skill-list odd glim-skills">
|
||||||
<li></li>
|
{{#each skills.glim as | skill |}}
|
||||||
<li></li>
|
{{#if skill}}
|
||||||
<li></li>
|
<li data-item-id="{{skill.uuid}}" data-ctx-menu="skill">
|
||||||
<li></li>
|
<span class="name">{{ skill.name }}</span>
|
||||||
|
<rc-icon
|
||||||
|
name="icons/info-circle"
|
||||||
|
var:size="16px"
|
||||||
|
var:fill="currentColor"
|
||||||
|
data-tooltip="{{ skill.use }}"
|
||||||
|
data-tooltip-direction="UP"
|
||||||
|
></rc-icon>
|
||||||
|
</li>
|
||||||
|
{{else}}
|
||||||
|
<li></li>
|
||||||
|
{{/if}}
|
||||||
|
{{/each}}
|
||||||
</ol>
|
</ol>
|
||||||
|
|
||||||
<div class="label col-header list-header">
|
<div class="label col-header list-header">
|
||||||
|
|
|
||||||
|
|
@ -41,7 +41,10 @@
|
||||||
grid-template-rows: subgrid;
|
grid-template-rows: subgrid;
|
||||||
|
|
||||||
& > li {
|
& > li {
|
||||||
padding-left: 4px;
|
padding: 0 4px;
|
||||||
|
.name {
|
||||||
|
flex-grow: 1;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
&.even > :nth-child(even),
|
&.even > :nth-child(even),
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue