Files
Foundry-VTT-Docker/resources/app/client-esm/applications/apps/permission-config.mjs
2025-01-04 00:34:03 +01:00

153 lines
4.9 KiB
JavaScript

import ApplicationV2 from "../api/application.mjs";
import HandlebarsApplicationMixin from "../api/handlebars-application.mjs";
/**
* An application for configuring the permissions which are available to each User role.
* @extends ApplicationV2
* @mixes HandlebarsApplication
* @alias PermissionConfig
*/
export default class PermissionConfig extends HandlebarsApplicationMixin(ApplicationV2) {
/** @inheritDoc */
static DEFAULT_OPTIONS = {
id: "permissions-config",
tag: "form",
window: {
contentClasses: ["standard-form"],
icon: "fa-solid fa-shield-keyhole",
title: "PERMISSION.Title",
},
position: {
width: 660,
height: "auto"
},
form: {
closeOnSubmit: true,
handler: PermissionConfig.#onSubmit
},
actions: {
reset: PermissionConfig.#onReset
}
};
/** @override */
static PARTS = {
permissions: {
id: "permissions",
template: "templates/apps/permission-config.hbs",
scrollable: [".permissions-list"]
},
footer: {
template: "templates/generic/form-footer.hbs"
}
};
/* -------------------------------------------- */
/* Rendering */
/* -------------------------------------------- */
/** @override */
async _prepareContext(_options={}) {
const current = await game.settings.get("core", "permissions");
return {
roles: Object.keys(CONST.USER_ROLES).reduce((obj, r) => {
if ( r === "NONE" ) return obj;
obj[r] = `USER.Role${r.titleCase()}`;
return obj;
}, {}),
permissions: this.#preparePermissions(current),
buttons: [
{type: "reset", action: "reset", icon: "fa-solid fa-sync", label: "PERMISSION.Reset"},
{type: "submit", icon: "fa-solid fa-save", label: "PERMISSION.Submit"}
]
};
}
/* -------------------------------------------- */
/**
* Prepare the permissions object used to render the configuration template
* @param {object} current The current permission configuration
* @returns {object[]} Permission data for sheet rendering
*/
#preparePermissions(current) {
const r = CONST.USER_ROLES;
const rgm = r.GAMEMASTER;
// Get permissions
const perms = Object.entries(CONST.USER_PERMISSIONS).reduce((arr, e) => {
const perm = foundry.utils.deepClone(e[1]);
perm.id = e[0];
perm.label = game.i18n.localize(perm.label);
perm.hint = game.i18n.localize(perm.hint);
arr.push(perm);
return arr;
}, []);
perms.sort((a, b) => a.label.localeCompare(b.label, game.i18n.lang));
// Configure permission roles
for ( let p of perms ) {
const roles = current[p.id] || Array.fromRange(rgm + 1).slice(p.defaultRole);
p.roles = Object.values(r).reduce((arr, role) => {
if ( role === r.NONE ) return arr;
arr.push({
name: `${p.id}.${role}`,
value: roles.includes(role),
readonly: (role === rgm) && (!p.disableGM) ? "readonly" : ""
});
return arr;
}, []);
}
return perms;
}
/* -------------------------------------------- */
/* Event Listeners and Handlers */
/* -------------------------------------------- */
/**
* Handle submission
* @this {DocumentSheetV2} The handler is called with the application as its bound scope
* @param {SubmitEvent} event The originating form submission event
* @param {HTMLFormElement} form The form element that was submitted
* @param {FormDataExtended} formData Processed data for the submitted form
* @returns {Promise<void>}
*/
static async #onSubmit(event, form, formData) {
const permissions = foundry.utils.expandObject(formData.object);
for ( let [k, v] of Object.entries(permissions) ) {
if ( !(k in CONST.USER_PERMISSIONS ) ) {
delete permissions[k];
continue;
}
permissions[k] = Object.entries(v).reduce((arr, r) => {
if ( r[1] === true ) arr.push(parseInt(r[0]));
return arr;
}, []);
}
await game.settings.set("core", "permissions", permissions);
ui.notifications.info("SETTINGS.PermissionUpdate", {localize: true});
}
/* -------------------------------------------- */
/**
* Handle click actions to reset all permissions back to their initial state.
* @this {PermissionConfig}
* @param {PointerEvent} event
* @returns {Promise<void>}
*/
static async #onReset(event) {
event.preventDefault();
const defaults = Object.entries(CONST.USER_PERMISSIONS).reduce((obj, [id, perm]) => {
obj[id] = Array.fromRange(CONST.USER_ROLES.GAMEMASTER + 1).slice(perm.defaultRole);
return obj;
}, {});
await game.settings.set("core", "permissions", defaults);
ui.notifications.info("SETTINGS.PermissionReset", {localize: true});
await this.render();
}
}