From 475c2b0932072e551258b13ca2b82b74c9c10009 Mon Sep 17 00:00:00 2001 From: Matheus Clemente Date: Thu, 9 Feb 2023 16:51:08 -0300 Subject: [PATCH 1/4] Prettier code formatting No changes to the logic, just formatting. --- .prettierignore | 1 + .prettierrc | 6 + app/js/Theatre.js | 8587 +++++++++++++++++----------------- app/js/TheatreActor.js | 8 +- app/js/TheatreActorConfig.js | 751 ++- app/js/theatre_main.js | 1584 +++---- 6 files changed, 5329 insertions(+), 5608 deletions(-) create mode 100644 .prettierignore create mode 100644 .prettierrc diff --git a/.prettierignore b/.prettierignore new file mode 100644 index 0000000..c79dc9b --- /dev/null +++ b/.prettierignore @@ -0,0 +1 @@ +app/js/TheatreActor.js \ No newline at end of file diff --git a/.prettierrc b/.prettierrc new file mode 100644 index 0000000..0f084a5 --- /dev/null +++ b/.prettierrc @@ -0,0 +1,6 @@ +{ + "printWidth": 180, + "tabWidth": 4, + "useTabs": true, + "endOfLine": "auto" +} diff --git a/app/js/Theatre.js b/app/js/Theatre.js index 28382a6..23d6dfb 100644 --- a/app/js/Theatre.js +++ b/app/js/Theatre.js @@ -14,12 +14,10 @@ * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License - * along with this program. If not, see . + * along with this program. If not, see . * */ - - /** * ============================================================ * Singleton Theatre @@ -31,83 +29,82 @@ * ============================================================ */ class Theatre { - /** - * Make singleton and initalize the inner instance object. - * Return singleton if already created. + * Make singleton and initalize the inner instance object. + * Return singleton if already created. */ constructor() { if (!Theatre.instance) { // build theater-wide statics - Theatre.SOCKET = "module.theatre"; - Theatre.SETTINGS = "theatre"; - Theatre.NARRATOR = "Narrator"; - Theatre.ICONLIB = "modules/theatre/app/graphics/emotes"; - Theatre.DEBUG = false; - Theatre.instance = this; - Theatre.textStandingAnimation(null); - Theatre.textFlyinAnimation(null); + Theatre.SOCKET = "module.theatre"; + Theatre.SETTINGS = "theatre"; + Theatre.NARRATOR = "Narrator"; + Theatre.ICONLIB = "modules/theatre/app/graphics/emotes"; + Theatre.DEBUG = false; + Theatre.instance = this; + Theatre.textStandingAnimation(null); + Theatre.textFlyinAnimation(null); // build theater variables // font related - this.titleFont = "Riffic"; - this.textFont = "SignikaBold"; - this.fontWeight = "bold"; + this.titleFont = "Riffic"; + this.textFont = "SignikaBold"; + this.fontWeight = "bold"; // position/order related - this.reorderTOId = null; - this.swapTarget = null; - this.dragPoint = null; - this.dragNavItem = null; + this.reorderTOId = null; + this.swapTarget = null; + this.dragPoint = null; + this.dragNavItem = null; // toggle related - this.isNarratorActive = false; - this.isSuppressed = false; - this.isQuoteAuto = false; - this.isDelayEmote = false; - this.delayedSentState = 0; + this.isNarratorActive = false; + this.isSuppressed = false; + this.isQuoteAuto = false; + this.isDelayEmote = false; + this.delayedSentState = 0; // render related - this.rendering = false; - this.renderAnims = 0; + this.rendering = false; + this.renderAnims = 0; // global insert state related this.speakingAs = null; // Map of theatreId to TheatreActor this.stage = {}; - this.portraitDocks = []; - this.userEmotes = {}; - this.usersTyping = {}; - this.userSettings = {}; - this.pixiCTX = null; - this.pixiToolTipCTX = null; - this.lastTyping = 0; + this.portraitDocks = []; + this.userEmotes = {}; + this.usersTyping = {}; + this.userSettings = {}; + this.pixiCTX = null; + this.pixiToolTipCTX = null; + this.lastTyping = 0; this.resync = { type: "any", - timeoutId: null - }; + timeoutId: null, + }; // configurable settings this.settings = { autoDecay: true, decayRate: 1000, decayMin: 30000, barStyle: "textbox", - narrHeight: "50%" - } + narrHeight: "50%", + }; // Font library - Theatre.getFonts(); + Theatre.getFonts(); // FaceAPI - //this._initFaceAPI(); + //this._initFaceAPI(); // module settings - this._initModuleSettings(); + this._initModuleSettings(); } - return Theatre.instance; + return Theatre.instance; } initialize() { // inject HTML - this._injectHTML(); - // socket - this._initSocket(); + this._injectHTML(); + // socket + this._initSocket(); // global listeners - window.addEventListener("resize",this.handleWindowResize); + window.addEventListener("resize", this.handleWindowResize); // request a resync if needed - this._sendResyncRequest("any"); + this._sendResyncRequest("any"); } /** @@ -116,164 +113,163 @@ class Theatre { * @private */ _injectHTML() { - /** * Theatre Dock + Theatre Bar */ - let body = document.getElementsByTagName("body")[0]; - let chatSidebar = document.getElementById("chat"); + let body = document.getElementsByTagName("body")[0]; + let chatSidebar = document.getElementById("chat"); - this.theatreGroup = document.createElement("div"); - this.theatreDock = this._initTheatreDockCanvas(); - this.theatreToolTip = this._initTheatreToolTip(); + this.theatreGroup = document.createElement("div"); + this.theatreDock = this._initTheatreDockCanvas(); + this.theatreToolTip = this._initTheatreToolTip(); if (!this.theatreDock || !this.theatreToolTip) { - console.error("Theatre encountered a FATAL error during initialization"); - ui.notifications.error(game.i18n.localize("Theatre.UI.Notification.Fatal")); - return; - } - - this.theatreGroup.id = "theatre-group"; - this.theatreDock.id = "theatre-dock"; - this.theatreToolTip.id = "theatre-tooltip"; - this.theatreBar = document.createElement("div"); - this.theatreBar.id = "theatre-bar"; - this.theatreNarrator = document.createElement("div"); - this.theatreNarrator.id = "theatre-narrator"; - //this.theatreError = document.createElement("div"); - //this.theatreError.id = "theatre-error"; - - let barContainerPrime = document.createElement("div"); - let barContainerSecond = document.createElement("div"); - barContainerPrime.id = "theatre-prime-bar"; - barContainerSecond.id = "theatre-second-bar"; - - let narratorBackdrop = document.createElement("div"); - let narratorContent = document.createElement("div"); - - KHelpers.addClass(barContainerPrime,"theatre-bar-left"); - KHelpers.addClass(barContainerSecond,"theatre-bar-right"); - KHelpers.addClass(narratorBackdrop,"theatre-narrator-backdrop"); - KHelpers.addClass(narratorContent,"theatre-narrator-content"); - KHelpers.addClass(narratorContent,"no-scrollbar"); - KHelpers.addClass(this.theatreGroup,"theatre-group"); - KHelpers.addClass(this.theatreDock,"theatre-dock"); - KHelpers.addClass(this.theatreDock,"no-scrollbar"); - KHelpers.addClass(this.theatreBar,"theatre-bar"); - KHelpers.addClass(this.theatreNarrator,"theatre-narrator"); - - this.theatreNarrator.appendChild(narratorBackdrop); - this.theatreNarrator.appendChild(narratorContent); - - this.theatreBar.appendChild(barContainerPrime); - this.theatreBar.appendChild(barContainerSecond); - - this.theatreGroup.appendChild(this.theatreDock); - this.theatreGroup.appendChild(this.theatreBar); + console.error("Theatre encountered a FATAL error during initialization"); + ui.notifications.error(game.i18n.localize("Theatre.UI.Notification.Fatal")); + return; + } + + this.theatreGroup.id = "theatre-group"; + this.theatreDock.id = "theatre-dock"; + this.theatreToolTip.id = "theatre-tooltip"; + this.theatreBar = document.createElement("div"); + this.theatreBar.id = "theatre-bar"; + this.theatreNarrator = document.createElement("div"); + this.theatreNarrator.id = "theatre-narrator"; + //this.theatreError = document.createElement("div"); + //this.theatreError.id = "theatre-error"; + + let barContainerPrime = document.createElement("div"); + let barContainerSecond = document.createElement("div"); + barContainerPrime.id = "theatre-prime-bar"; + barContainerSecond.id = "theatre-second-bar"; + + let narratorBackdrop = document.createElement("div"); + let narratorContent = document.createElement("div"); + + KHelpers.addClass(barContainerPrime, "theatre-bar-left"); + KHelpers.addClass(barContainerSecond, "theatre-bar-right"); + KHelpers.addClass(narratorBackdrop, "theatre-narrator-backdrop"); + KHelpers.addClass(narratorContent, "theatre-narrator-content"); + KHelpers.addClass(narratorContent, "no-scrollbar"); + KHelpers.addClass(this.theatreGroup, "theatre-group"); + KHelpers.addClass(this.theatreDock, "theatre-dock"); + KHelpers.addClass(this.theatreDock, "no-scrollbar"); + KHelpers.addClass(this.theatreBar, "theatre-bar"); + KHelpers.addClass(this.theatreNarrator, "theatre-narrator"); + + this.theatreNarrator.appendChild(narratorBackdrop); + this.theatreNarrator.appendChild(narratorContent); + + this.theatreBar.appendChild(barContainerPrime); + this.theatreBar.appendChild(barContainerSecond); + + this.theatreGroup.appendChild(this.theatreDock); + this.theatreGroup.appendChild(this.theatreBar); this.theatreGroup.appendChild(this.theatreNarrator); - this.theatreGroup.appendChild(this.theatreToolTip); + this.theatreGroup.appendChild(this.theatreToolTip); - body.appendChild(this.theatreGroup); + body.appendChild(this.theatreGroup); // set theatreStyle - this.settings.theatreStyle = game.settings.get(Theatre.SETTINGS,"theatreStyle"); - this.configTheatreStyle(this.settings.theatreStyle); + this.settings.theatreStyle = game.settings.get(Theatre.SETTINGS, "theatreStyle"); + this.configTheatreStyle(this.settings.theatreStyle); // set narrator height - this.settings.narrHeight = game.settings.get(Theatre.SETTINGS,"theatreNarratorHeight"); - this.theatreNarrator.style.top = `calc(${this.settings.narrHeight} - 50px)`; + this.settings.narrHeight = game.settings.get(Theatre.SETTINGS, "theatreNarratorHeight"); + this.theatreNarrator.style.top = `calc(${this.settings.narrHeight} - 50px)`; // set dock canvas hard dimensions after CSS has caclulated it /** * Theatre Chat Controls */ - let chatControls = document.getElementById("chat-controls"); - let controlButtons = chatControls.getElementsByClassName("control-buttons")[0]; - let chatForm = document.getElementById("chat-form"); - let chatMessage = document.getElementById("chat-message"); + let chatControls = document.getElementById("chat-controls"); + let controlButtons = chatControls.getElementsByClassName("control-buttons")[0]; + let chatForm = document.getElementById("chat-form"); + let chatMessage = document.getElementById("chat-message"); - this.theatreControls = document.createElement("div"); - this.theatreNavBar = document.createElement("div"); - this.theatreChatCover = document.createElement("div"); + this.theatreControls = document.createElement("div"); + this.theatreNavBar = document.createElement("div"); + this.theatreChatCover = document.createElement("div"); if (!game.user.isGM && game.settings.get(Theatre.SETTINGS, "gmOnly")) { this.theatreControls.style.display = "none"; } - let imgCover = document.createElement("img"); - let btnSuppress = document.createElement("div"); - let iconSuppress = document.createElement("div"); - let btnEmote = document.createElement("div"); - let iconEmote = document.createElement("div"); - //let btnCinema = document.createElement("div"); - //let iconCinema = document.createElement("div"); - let btnNarrator; - let iconNarrator; - - let btnResync = document.createElement("a"); - let iconResync = document.createElement("i"); - let btnQuote = document.createElement("a"); - let iconQuote = document.createElement("i"); - let btnDelayEmote = document.createElement("a"); - let iconDelayEmote = document.createElement("i"); - - KHelpers.addClass(this.theatreControls,"theatre-control-group"); - KHelpers.addClass(this.theatreNavBar,"theatre-control-nav-bar"); - KHelpers.addClass(this.theatreNavBar,"no-scrollbar"); - KHelpers.addClass(this.theatreChatCover,"theatre-control-chat-cover"); - KHelpers.addClass(btnSuppress,"theatre-control-btn"); - KHelpers.addClass(iconSuppress,"theatre-icon-suppress"); - KHelpers.addClass(btnEmote,"theatre-control-btn"); - KHelpers.addClass(iconEmote,"theatre-icon-emote"); - //KHelpers.addClass(btnCinema,"theatre-control-btn"); - //KHelpers.addClass(iconCinema,"theatre-icon-cinema"); - KHelpers.addClass(btnResync,"button"); - KHelpers.addClass(btnResync,"resync-theatre"); - KHelpers.addClass(iconResync,"fas"); - KHelpers.addClass(iconResync,"fa-sync"); - KHelpers.addClass(btnQuote,"button"); - KHelpers.addClass(iconQuote,"fas"); - KHelpers.addClass(iconQuote,"fa-quote-right"); - KHelpers.addClass(btnDelayEmote,"button"); - KHelpers.addClass(iconDelayEmote,"fas"); - KHelpers.addClass(iconDelayEmote,"fa-comment-alt"); - - btnEmote.setAttribute("title",game.i18n.localize("Theatre.UI.Title.EmoteSelector")); - btnSuppress.setAttribute("title",game.i18n.localize("Theatre.UI.Title.SuppressTheatre")); - btnResync.setAttribute("title",(game.user.isGM ? game.i18n.localize("Theatre.UI.Title.ResyncGM") : game.i18n.localize("Theatre.UI.Title.ResyncPlayer"))); - btnQuote.setAttribute("title",game.i18n.localize("Theatre.UI.Title.QuoteToggle")); - btnDelayEmote.setAttribute("title",game.i18n.localize("Theatre.UI.Title.DelayEmoteToggle")); - //btnCinema.setAttribute("title",game.i18n.localize("Theatre.UI.Title.CinemaSelector")); - btnEmote.addEventListener("click", this.handleBtnEmoteClick); - btnSuppress.addEventListener("click", this.handleBtnSuppressClick); - btnResync.addEventListener("click", this.handleBtnResyncClick); - btnQuote.addEventListener("click", this.handleBtnQuoteClick); - btnDelayEmote.addEventListener("click", this.handleBtnDelayEmoteClick); - //btnCinema.addEventListener("click", this.handleBtnCinemaClick); - this.theatreNavBar.addEventListener("wheel", this.handleNavBarWheel); - - btnEmote.appendChild(iconEmote); - btnSuppress.appendChild(iconSuppress); - btnResync.appendChild(iconResync); - btnQuote.appendChild(iconQuote); - btnDelayEmote.appendChild(iconDelayEmote); - //btnCinema.appendChild(iconCinema); - this.theatreChatCover.appendChild(imgCover); - - this.theatreControls.appendChild(this.theatreNavBar); + let imgCover = document.createElement("img"); + let btnSuppress = document.createElement("div"); + let iconSuppress = document.createElement("div"); + let btnEmote = document.createElement("div"); + let iconEmote = document.createElement("div"); + //let btnCinema = document.createElement("div"); + //let iconCinema = document.createElement("div"); + let btnNarrator; + let iconNarrator; + + let btnResync = document.createElement("a"); + let iconResync = document.createElement("i"); + let btnQuote = document.createElement("a"); + let iconQuote = document.createElement("i"); + let btnDelayEmote = document.createElement("a"); + let iconDelayEmote = document.createElement("i"); + + KHelpers.addClass(this.theatreControls, "theatre-control-group"); + KHelpers.addClass(this.theatreNavBar, "theatre-control-nav-bar"); + KHelpers.addClass(this.theatreNavBar, "no-scrollbar"); + KHelpers.addClass(this.theatreChatCover, "theatre-control-chat-cover"); + KHelpers.addClass(btnSuppress, "theatre-control-btn"); + KHelpers.addClass(iconSuppress, "theatre-icon-suppress"); + KHelpers.addClass(btnEmote, "theatre-control-btn"); + KHelpers.addClass(iconEmote, "theatre-icon-emote"); + //KHelpers.addClass(btnCinema,"theatre-control-btn"); + //KHelpers.addClass(iconCinema,"theatre-icon-cinema"); + KHelpers.addClass(btnResync, "button"); + KHelpers.addClass(btnResync, "resync-theatre"); + KHelpers.addClass(iconResync, "fas"); + KHelpers.addClass(iconResync, "fa-sync"); + KHelpers.addClass(btnQuote, "button"); + KHelpers.addClass(iconQuote, "fas"); + KHelpers.addClass(iconQuote, "fa-quote-right"); + KHelpers.addClass(btnDelayEmote, "button"); + KHelpers.addClass(iconDelayEmote, "fas"); + KHelpers.addClass(iconDelayEmote, "fa-comment-alt"); + + btnEmote.setAttribute("title", game.i18n.localize("Theatre.UI.Title.EmoteSelector")); + btnSuppress.setAttribute("title", game.i18n.localize("Theatre.UI.Title.SuppressTheatre")); + btnResync.setAttribute("title", game.user.isGM ? game.i18n.localize("Theatre.UI.Title.ResyncGM") : game.i18n.localize("Theatre.UI.Title.ResyncPlayer")); + btnQuote.setAttribute("title", game.i18n.localize("Theatre.UI.Title.QuoteToggle")); + btnDelayEmote.setAttribute("title", game.i18n.localize("Theatre.UI.Title.DelayEmoteToggle")); + //btnCinema.setAttribute("title",game.i18n.localize("Theatre.UI.Title.CinemaSelector")); + btnEmote.addEventListener("click", this.handleBtnEmoteClick); + btnSuppress.addEventListener("click", this.handleBtnSuppressClick); + btnResync.addEventListener("click", this.handleBtnResyncClick); + btnQuote.addEventListener("click", this.handleBtnQuoteClick); + btnDelayEmote.addEventListener("click", this.handleBtnDelayEmoteClick); + //btnCinema.addEventListener("click", this.handleBtnCinemaClick); + this.theatreNavBar.addEventListener("wheel", this.handleNavBarWheel); + + btnEmote.appendChild(iconEmote); + btnSuppress.appendChild(iconSuppress); + btnResync.appendChild(iconResync); + btnQuote.appendChild(iconQuote); + btnDelayEmote.appendChild(iconDelayEmote); + //btnCinema.appendChild(iconCinema); + this.theatreChatCover.appendChild(imgCover); + + this.theatreControls.appendChild(this.theatreNavBar); if (game.user.isGM) { - btnNarrator = document.createElement("div"); - iconNarrator = document.createElement("div"); - KHelpers.addClass(btnNarrator,"theatre-control-btn"); - KHelpers.addClass(iconNarrator,"theatre-icon-narrator"); - btnNarrator.setAttribute("title",game.i18n.localize("Theatre.UI.Title.Narrator")); - btnNarrator.appendChild(iconNarrator); - btnNarrator.addEventListener("click",this.handleBtnNarratorClick); - this.theatreControls.appendChild(btnNarrator); + btnNarrator = document.createElement("div"); + iconNarrator = document.createElement("div"); + KHelpers.addClass(btnNarrator, "theatre-control-btn"); + KHelpers.addClass(iconNarrator, "theatre-icon-narrator"); + btnNarrator.setAttribute("title", game.i18n.localize("Theatre.UI.Title.Narrator")); + btnNarrator.appendChild(iconNarrator); + btnNarrator.addEventListener("click", this.handleBtnNarratorClick); + this.theatreControls.appendChild(btnNarrator); } - this.theatreControls.appendChild(btnEmote); - //this.theatreControls.appendChild(btnCinema); - this.theatreControls.appendChild(btnSuppress); + this.theatreControls.appendChild(btnEmote); + //this.theatreControls.appendChild(btnCinema); + this.theatreControls.appendChild(btnSuppress); btnDelayEmote.style["margin"] = "0 4px"; btnQuote.style["margin"] = "0 4px"; @@ -282,12 +278,12 @@ class Theatre { if (game.user.isGM || !game.settings.get(Theatre.SETTINGS, "gmOnly")) { if (controlButtons) { controlButtons.style["flex-basis"] = "150px"; - KHelpers.insertBefore(btnResync,controlButtons.children[0]); - KHelpers.insertBefore(btnQuote,btnResync); - KHelpers.insertBefore(btnDelayEmote,btnQuote); + KHelpers.insertBefore(btnResync, controlButtons.children[0]); + KHelpers.insertBefore(btnQuote, btnResync); + KHelpers.insertBefore(btnDelayEmote, btnQuote); } else { controlButtons = document.createElement("div"); - KHelpers.addClass(controlButtons,"control-buttons"); + KHelpers.addClass(controlButtons, "control-buttons"); controlButtons.style["flex-basis"] = "66px"; controlButtons.appendChild(btnDelayEmote); controlButtons.appendChild(btnQuote); @@ -296,26 +292,26 @@ class Theatre { } } - KHelpers.insertBefore(this.theatreControls,chatControls); - KHelpers.insertAfter(this.theatreChatCover,chatMessage); + KHelpers.insertBefore(this.theatreControls, chatControls); + KHelpers.insertAfter(this.theatreChatCover, chatMessage); // bind listener to chat message - chatMessage.addEventListener("keydown",this.handleChatMessageKeyDown); - chatMessage.addEventListener("keyup",this.handleChatMessageKeyUp); - chatMessage.addEventListener("focusout",this.handleChatMessageFocusOut); + chatMessage.addEventListener("keydown", this.handleChatMessageKeyDown); + chatMessage.addEventListener("keyup", this.handleChatMessageKeyUp); + chatMessage.addEventListener("focusout", this.handleChatMessageFocusOut); /* - * Emote Menu - */ - this.theatreEmoteMenu = document.createElement("div"); - KHelpers.addClass(this.theatreEmoteMenu,"theatre-emote-menu"); - KHelpers.addClass(this.theatreEmoteMenu,"app"); - KHelpers.insertBefore(this.theatreEmoteMenu,this.theatreControls); + * Emote Menu + */ + this.theatreEmoteMenu = document.createElement("div"); + KHelpers.addClass(this.theatreEmoteMenu, "theatre-emote-menu"); + KHelpers.addClass(this.theatreEmoteMenu, "app"); + KHelpers.insertBefore(this.theatreEmoteMenu, this.theatreControls); /** * Tooltip */ - this.theatreEmoteMenu.addEventListener("mousemove",this.handleEmoteMenuMouseMove); + this.theatreEmoteMenu.addEventListener("mousemove", this.handleEmoteMenuMouseMove); } /** @@ -333,7 +329,9 @@ class Theatre { config: true, default: false, type: Boolean, - onChange: () => {if (!game.user.isGM) location.reload();}, + onChange: () => { + if (!game.user.isGM) location.reload(); + }, }); game.settings.register(Theatre.SETTINGS, "theatreStyle", { @@ -344,11 +342,11 @@ class Theatre { default: "textbox", type: String, choices: { - "textbox": "Theatre.UI.Settings.displayModeTextBox", - "lightbox": "Theatre.UI.Settings.displayModeLightBox", - "clearbox": "Theatre.UI.Settings.displayModeClearBox" + textbox: "Theatre.UI.Settings.displayModeTextBox", + lightbox: "Theatre.UI.Settings.displayModeLightBox", + clearbox: "Theatre.UI.Settings.displayModeClearBox", }, - onChange: theatreStyle => Theatre.instance.configTheatreStyle(theatreStyle) + onChange: (theatreStyle) => Theatre.instance.configTheatreStyle(theatreStyle), }); game.settings.register(Theatre.SETTINGS, "theatreImageSize", { @@ -357,7 +355,7 @@ class Theatre { config: true, default: 400, type: Number, - }); + }); game.settings.register(Theatre.SETTINGS, "theatreNarratorHeight", { name: "Theatre.UI.Settings.narrHeight", @@ -371,13 +369,12 @@ class Theatre { "25%": "25%", "30%": "30%", "50%": "50%", - "70%": "75%" + "70%": "75%", + }, + onChange: (narrHeight) => { + this.settings.narrHeight = narrHeight; + if (this.theatreNarrator) this.theatreNarrator.style.top = `calc(${narrHeight} - 50px)`; }, - onChange: narrHeight => { - this.settings.narrHeight = narrHeight; - if (this.theatreNarrator) - this.theatreNarrator.style.top = `calc(${narrHeight} - 50px)`; - } }); game.settings.register(Theatre.SETTINGS, "nameFont", { @@ -387,9 +384,10 @@ class Theatre { config: true, default: Theatre.instance.titleFont, type: String, - choices: Theatre.FONTS.reduce((a, font) => { a[font]=font; - return a; - }, {}), + choices: Theatre.FONTS.reduce((a, font) => { + a[font] = font; + return a; + }, {}), }); game.settings.register(Theatre.SETTINGS, "nameFontSize", { @@ -400,7 +398,7 @@ class Theatre { default: 44, type: Number, }); - + game.settings.register(Theatre.SETTINGS, "textDecayMin", { name: "Theatre.UI.Settings.textDecayMin", hint: "Theatre.UI.Settings.textDecayMinHint", @@ -408,22 +406,22 @@ class Theatre { config: true, default: 30, type: Number, - onChange: textDecayMin => { - if (Theatre.DEBUG) console.log("Text decay minimum set to %s",textDecayMin); - textDecayMin = Number(textDecayMin); - if(isNaN(textDecayMin) || textDecayMin <= 0) { - ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.InvalidDecayMin")); - game.settings.set(Theatre.SETTINGS,"textDecayMin",30); - return; + onChange: (textDecayMin) => { + if (Theatre.DEBUG) console.log("Text decay minimum set to %s", textDecayMin); + textDecayMin = Number(textDecayMin); + if (isNaN(textDecayMin) || textDecayMin <= 0) { + ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.InvalidDecayMin")); + game.settings.set(Theatre.SETTINGS, "textDecayMin", 30); + return; } - if(textDecayMin > 600) { - ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.TooLongDecayMin")); - game.settings.set(Theatre.SETTINGS,"textDecayMin",600); - return; + if (textDecayMin > 600) { + ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.TooLongDecayMin")); + game.settings.set(Theatre.SETTINGS, "textDecayMin", 600); + return; } - this.settings.decayMin = textDecayMin*1000; - } + this.settings.decayMin = textDecayMin * 1000; + }, }); game.settings.register(Theatre.SETTINGS, "textDecayRate", { @@ -433,23 +431,23 @@ class Theatre { config: true, default: 1, type: Number, - onChange: textDecayRate => { - if (Theatre.DEBUG) console.log("Text decay rate set to %s",textDecayRate); - textDecayRate = Number(textDecayRate); - if(isNaN(textDecayRate) || textDecayRate <= 0) { - textDecayRate = 1; - ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.InvalidDecayRate")); - game.settings.set(Theatre.SETTINGS,"textDecayRate",1); - return; + onChange: (textDecayRate) => { + if (Theatre.DEBUG) console.log("Text decay rate set to %s", textDecayRate); + textDecayRate = Number(textDecayRate); + if (isNaN(textDecayRate) || textDecayRate <= 0) { + textDecayRate = 1; + ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.InvalidDecayRate")); + game.settings.set(Theatre.SETTINGS, "textDecayRate", 1); + return; } if (textDecayRate > 10) { - textDecayRate = 10; - ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.TooLongDecayRate")); - game.settings.set(Theatre.SETTINGS,"textDecayRate",10); - return; + textDecayRate = 10; + ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.TooLongDecayRate")); + game.settings.set(Theatre.SETTINGS, "textDecayRate", 10); + return; } - this.settings.decayRate = textDecayRate*1000; - } + this.settings.decayRate = textDecayRate * 1000; + }, }); game.settings.register(Theatre.SETTINGS, "motdNewInfo", { @@ -457,43 +455,42 @@ class Theatre { scope: "client", default: 0, type: Number, - onChange: newInfo => { + onChange: (newInfo) => { // NOOP - } + }, }); - + game.settings.register(Theatre.SETTINGS, "autoHideBottom", { name: "Theatre.UI.Settings.autoHideBottom", - hint: "Theatre.UI.Settings.autoHideBottomHint", - scope: "world", - config: true, - type: Boolean, - default: true + hint: "Theatre.UI.Settings.autoHideBottomHint", + scope: "world", + config: true, + type: Boolean, + default: true, }); game.settings.register(Theatre.SETTINGS, "suppressMacroHotbar", { name: "Theatre.UI.Settings.suppressMacroHotbar", - hint: "", - scope: "world", - config: true, - type: Boolean, - default: true + hint: "", + scope: "world", + config: true, + type: Boolean, + default: true, }); game.settings.register(Theatre.SETTINGS, "removeLabelSheetHeader", { name: "Theatre.UI.Settings.removeLabelSheetHeader", - hint: "Theatre.UI.Settings.removeLabelSheetHeaderHint", - scope: "world", - config: true, - type: Boolean, - default: false + hint: "Theatre.UI.Settings.removeLabelSheetHeaderHint", + scope: "world", + config: true, + type: Boolean, + default: false, }); // Load in default settings (theatreStyle is loaded on HTML Injection) - this.settings.decayMin = (game.settings.get(Theatre.SETTINGS,"textDecayMin")||30)*1000; - this.settings.decayRate = (game.settings.get(Theatre.SETTINGS,"textDecayRate")||1)*1000; - this.settings.motdNewInfo = game.settings.get(Theatre.SETTINGS,"motdNewInfo")||1; - + this.settings.decayMin = (game.settings.get(Theatre.SETTINGS, "textDecayMin") || 30) * 1000; + this.settings.decayRate = (game.settings.get(Theatre.SETTINGS, "textDecayRate") || 1) * 1000; + this.settings.motdNewInfo = game.settings.get(Theatre.SETTINGS, "motdNewInfo") || 1; } /** @@ -502,107 +499,102 @@ class Theatre { * @param theatreStyle (String) : The theatre Style to apply */ configTheatreStyle(theatreStyle) { - if (Theatre.DEBUG) console.log("SWITCHING THEATRE BAR MODE : %s from %s",theatreStyle,this.settings.theatreStyle); - let oldStyle = this.settings.theatreStyle; - let primeBar = document.getElementById("theatre-prime-bar"); + if (Theatre.DEBUG) console.log("SWITCHING THEATRE BAR MODE : %s from %s", theatreStyle, this.settings.theatreStyle); + let oldStyle = this.settings.theatreStyle; + let primeBar = document.getElementById("theatre-prime-bar"); let secondBar = document.getElementById("theatre-second-bar"); - let textBoxes = this._getTextBoxes(); + let textBoxes = this._getTextBoxes(); // - //let app = Theatre.instance.pixiCTX; - let dockWidth = this.theatreDock.offsetWidth; - let dockHeight = this.theatreDock.offsetHeight; + //let app = Theatre.instance.pixiCTX; + let dockWidth = this.theatreDock.offsetWidth; + let dockHeight = this.theatreDock.offsetHeight; // clear old style switch (oldStyle || "textbox") { case "lightbox": - KHelpers.removeClass(primeBar,"theatre-bar-left"); - KHelpers.removeClass(secondBar,"theatre-bar-right"); - KHelpers.removeClass(primeBar,"theatre-bar-lightleft"); - KHelpers.removeClass(secondBar,"theatre-bar-lightright"); + KHelpers.removeClass(primeBar, "theatre-bar-left"); + KHelpers.removeClass(secondBar, "theatre-bar-right"); + KHelpers.removeClass(primeBar, "theatre-bar-lightleft"); + KHelpers.removeClass(secondBar, "theatre-bar-lightright"); for (let tb of textBoxes) { - KHelpers.removeClass(tb,"theatre-text-box-light"); - KHelpers.removeClass(tb,"theatre-text-box"); + KHelpers.removeClass(tb, "theatre-text-box-light"); + KHelpers.removeClass(tb, "theatre-text-box"); } - break; + break; case "clearbox": - KHelpers.removeClass(primeBar,"theatre-bar-left"); - KHelpers.removeClass(secondBar,"theatre-bar-right"); - KHelpers.removeClass(primeBar,"theatre-bar-clearleft"); - KHelpers.removeClass(secondBar,"theatre-bar-clearright"); + KHelpers.removeClass(primeBar, "theatre-bar-left"); + KHelpers.removeClass(secondBar, "theatre-bar-right"); + KHelpers.removeClass(primeBar, "theatre-bar-clearleft"); + KHelpers.removeClass(secondBar, "theatre-bar-clearright"); for (let tb of textBoxes) { - KHelpers.removeClass(tb,"theatre-text-box-clear"); - KHelpers.removeClass(tb,"theatre-text-box"); + KHelpers.removeClass(tb, "theatre-text-box-clear"); + KHelpers.removeClass(tb, "theatre-text-box"); } - break; + break; case "mangabubble": - KHelpers.removeClass(primeBar,"theatre-bar-left"); - KHelpers.removeClass(secondBar,"theatre-bar-right"); + KHelpers.removeClass(primeBar, "theatre-bar-left"); + KHelpers.removeClass(secondBar, "theatre-bar-right"); for (let tb of textBoxes) { - KHelpers.removeClass(tb,"theatre-text-box"); + KHelpers.removeClass(tb, "theatre-text-box"); } // PLACEHOLDER FOR FUTURE - break; + break; case "textbox": default: - KHelpers.removeClass(primeBar,"theatre-bar-left"); - KHelpers.removeClass(secondBar,"theatre-bar-right"); - for (let tb of textBoxes) - KHelpers.removeClass(tb,"theatre-text-box"); - break; + KHelpers.removeClass(primeBar, "theatre-bar-left"); + KHelpers.removeClass(secondBar, "theatre-bar-right"); + for (let tb of textBoxes) KHelpers.removeClass(tb, "theatre-text-box"); + break; } // apply new style switch (theatreStyle) { case "lightbox": - KHelpers.addClass(primeBar,"theatre-bar-lightleft"); - KHelpers.addClass(secondBar,"theatre-bar-lightright"); - this.theatreDock.style.height = "100%"; - this.theatreBar.style.top = "calc(100% - 170px)"; - this.theatreBar.style.height = "170px"; - this.theatreBar.style["border-radius"] = "5px 0px 0px 5px"; - this.theatreBar.style["box-shadow"] = "0 0 40px #000"; - this.theatreBar.style.background = "linear-gradient(transparent, rgba(20,20,20,0.98) 5%,rgba(20,20,20,0.85) 40%, rgba(20,20,20,0.6) 70%, rgba(20,20,20,0.5) 95%)"; - for (let tb of textBoxes) - KHelpers.addClass(tb,"theatre-text-box-light"); - break; + KHelpers.addClass(primeBar, "theatre-bar-lightleft"); + KHelpers.addClass(secondBar, "theatre-bar-lightright"); + this.theatreDock.style.height = "100%"; + this.theatreBar.style.top = "calc(100% - 170px)"; + this.theatreBar.style.height = "170px"; + this.theatreBar.style["border-radius"] = "5px 0px 0px 5px"; + this.theatreBar.style["box-shadow"] = "0 0 40px #000"; + this.theatreBar.style.background = "linear-gradient(transparent, rgba(20,20,20,0.98) 5%,rgba(20,20,20,0.85) 40%, rgba(20,20,20,0.6) 70%, rgba(20,20,20,0.5) 95%)"; + for (let tb of textBoxes) KHelpers.addClass(tb, "theatre-text-box-light"); + break; case "clearbox": - KHelpers.addClass(primeBar,"theatre-bar-clearleft"); - KHelpers.addClass(secondBar,"theatre-bar-clearright"); - this.theatreDock.style.height = "100%"; - this.theatreBar.style.top = "calc(100% - 170px)"; - this.theatreBar.style.height = "170px"; - this.theatreBar.style["border-radius"] = "unset"; - this.theatreBar.style["box-shadow"] = "unset"; - this.theatreBar.style.background = "unset"; - for (let tb of textBoxes) - KHelpers.addClass(tb,"theatre-text-box-clear"); - break; + KHelpers.addClass(primeBar, "theatre-bar-clearleft"); + KHelpers.addClass(secondBar, "theatre-bar-clearright"); + this.theatreDock.style.height = "100%"; + this.theatreBar.style.top = "calc(100% - 170px)"; + this.theatreBar.style.height = "170px"; + this.theatreBar.style["border-radius"] = "unset"; + this.theatreBar.style["box-shadow"] = "unset"; + this.theatreBar.style.background = "unset"; + for (let tb of textBoxes) KHelpers.addClass(tb, "theatre-text-box-clear"); + break; case "mangabubble": // PLACEHOLDER FOR FUTURE - break; + break; case "textbox": default: - KHelpers.addClass(primeBar,"theatre-bar-left"); - KHelpers.addClass(secondBar,"theatre-bar-right"); - this.theatreDock.style.height = "99.5vh"; - this.theatreBar.style.top = "calc(100% - 160px - 0.5vh)"; - this.theatreBar.style.height = "160px"; - this.theatreBar.style["border-radius"] = "unset"; - this.theatreBar.style["box-shadow"] = "unset"; - this.theatreBar.style.background = "unset"; - for (let tb of textBoxes) - KHelpers.addClass(tb,"theatre-text-box"); - break; + KHelpers.addClass(primeBar, "theatre-bar-left"); + KHelpers.addClass(secondBar, "theatre-bar-right"); + this.theatreDock.style.height = "99.5vh"; + this.theatreBar.style.top = "calc(100% - 160px - 0.5vh)"; + this.theatreBar.style.height = "160px"; + this.theatreBar.style["border-radius"] = "unset"; + this.theatreBar.style["box-shadow"] = "unset"; + this.theatreBar.style.background = "unset"; + for (let tb of textBoxes) KHelpers.addClass(tb, "theatre-text-box"); + break; } - this.settings.theatreStyle = theatreStyle; + this.settings.theatreStyle = theatreStyle; // re-render all inserts - for (let insert of this.portraitDocks) - this.renderInsertById(insert.imgId); + for (let insert of this.portraitDocks) this.renderInsertById(insert.imgId); // apply resize adjustments (ev is unused) - this.handleWindowResize(null); + this.handleWindowResize(null); } /** @@ -614,27 +606,26 @@ class Theatre { */ _initSocket() { // module socket - game.socket.on(Theatre.SOCKET, payload => { - if (Theatre.DEBUG) console.log("Received packet",payload) + game.socket.on(Theatre.SOCKET, (payload) => { + if (Theatre.DEBUG) console.log("Received packet", payload); switch (payload.type) { case "sceneevent": - this._processSceneEvent(payload.senderId,payload.subtype,payload.data); + this._processSceneEvent(payload.senderId, payload.subtype, payload.data); break; case "typingevent": - this._processTypingEvent(payload.senderId,payload.data); - break; + this._processTypingEvent(payload.senderId, payload.data); + break; case "resyncevent": - this._processResyncEvent(payload.subtype,payload.senderId,payload.data); - break; + this._processResyncEvent(payload.subtype, payload.senderId, payload.data); + break; case "reqresync": - this._processResyncRequest(payload.subtype,payload.senderId,payload.data); - break; + this._processResyncRequest(payload.subtype, payload.senderId, payload.data); + break; default: - console.log("UNKNOWN THEATRE EVENT TYPE %s",payload.type,payload); + console.log("UNKNOWN THEATRE EVENT TYPE %s", payload.type, payload); break; } }); - } /** @@ -664,21 +655,18 @@ class Theatre { * * @private */ - _sendSceneEvent(eventType,eventData) { - if (Theatre.DEBUG) console.log("Sending Scene state %s with payload: ",eventType, eventData) + _sendSceneEvent(eventType, eventData) { + if (Theatre.DEBUG) console.log("Sending Scene state %s with payload: ", eventType, eventData); - // Do we even need verification? There's no User Input outside of + // Do we even need verification? There's no User Input outside of // cookie cutter responses - game.socket.emit(Theatre.SOCKET, - { - senderId: game.user.id, - type: "sceneevent", - subtype: eventType, - data: eventData - } - ); - + game.socket.emit(Theatre.SOCKET, { + senderId: game.user.id, + type: "sceneevent", + subtype: eventType, + data: eventData, + }); } /** @@ -691,44 +679,39 @@ class Theatre { * @private */ _sendTypingEvent() { - if (Theatre.DEBUG) console.log("Sending Typing Event") - - let insert = this.getInsertById(this.speakingAs); - let insertEmote = this._getEmoteFromInsert(insert); - let insertTextFlyin = - (insert ? this._getTextFlyinFromInsert(insert) : (this.speakingAs == Theatre.NARRATOR ? this.theatreNarrator.getAttribute("textflyin") : "typewriter")); - let insertTextStanding = - (insert ? this._getTextStandingFromInsert(insert) : (this.speakingAs == Theatre.NARRATOR ? this.theatreNarrator.getAttribute("textstanding") : "none")); - let insertTextFont = - (insert ? this._getTextFontFromInsert(insert) : (this.speakingAs == Theatre.NARRATOR ? this.theatreNarrator.getAttribute("textfont") : null)); - let insertTextSize = - (insert ? this._getTextSizeFromInsert(insert) : (this.speakingAs == Theatre.NARRATOR ? this.theatreNarrator.getAttribute("textsize") : null)); - let insertTextColor = - (insert ? this._getTextColorFromInsert(insert) : (this.speakingAs == Theatre.NARRATOR ? this.theatreNarrator.getAttribute("textcolor") : null)); + if (Theatre.DEBUG) console.log("Sending Typing Event"); + + let insert = this.getInsertById(this.speakingAs); + let insertEmote = this._getEmoteFromInsert(insert); + let insertTextFlyin = insert ? this._getTextFlyinFromInsert(insert) : this.speakingAs == Theatre.NARRATOR ? this.theatreNarrator.getAttribute("textflyin") : "typewriter"; + let insertTextStanding = insert + ? this._getTextStandingFromInsert(insert) + : this.speakingAs == Theatre.NARRATOR + ? this.theatreNarrator.getAttribute("textstanding") + : "none"; + let insertTextFont = insert ? this._getTextFontFromInsert(insert) : this.speakingAs == Theatre.NARRATOR ? this.theatreNarrator.getAttribute("textfont") : null; + let insertTextSize = insert ? this._getTextSizeFromInsert(insert) : this.speakingAs == Theatre.NARRATOR ? this.theatreNarrator.getAttribute("textsize") : null; + let insertTextColor = insert ? this._getTextColorFromInsert(insert) : this.speakingAs == Theatre.NARRATOR ? this.theatreNarrator.getAttribute("textcolor") : null; let emotedata = { - emote: insertEmote, - textflyin: insertTextFlyin, + emote: insertEmote, + textflyin: insertTextFlyin, textstanding: insertTextStanding, textfont: insertTextFont, textsize: insertTextSize, - textcolor: insertTextColor - } - - game.socket.emit(Theatre.SOCKET, - { - senderId: game.user.id, - type: "typingevent", - data: { - insertid : this.speakingAs, - emotions: emotedata - } - }, - ); - + textcolor: insertTextColor, + }; + + game.socket.emit(Theatre.SOCKET, { + senderId: game.user.id, + type: "typingevent", + data: { + insertid: this.speakingAs, + emotions: emotedata, + }, + }); } - /** * Someone is asking for a re-sync event, so we broadcast the entire scene * state to this target individual @@ -738,23 +721,19 @@ class Theatre { * @private */ _sendResyncEvent(targetId) { - - let insertData = this._buildResyncData(); - if (Theatre.DEBUG) console.log("Sending RESYNC Event (isGM)%s (to)%s: ",game.user.isGM,targetId,insertData) - - game.socket.emit(Theatre.SOCKET, - { - senderId: game.user.id, - type: "resyncevent", - subtype: (game.user.isGM ? "gm" : "player"), - data: { - targetid: targetId, - insertdata: insertData, - narrator: this.isNarratorActive - } - }, - ); - + let insertData = this._buildResyncData(); + if (Theatre.DEBUG) console.log("Sending RESYNC Event (isGM)%s (to)%s: ", game.user.isGM, targetId, insertData); + + game.socket.emit(Theatre.SOCKET, { + senderId: game.user.id, + type: "resyncevent", + subtype: game.user.isGM ? "gm" : "player", + data: { + targetid: targetId, + insertdata: insertData, + narrator: this.isNarratorActive, + }, + }); } /** @@ -765,37 +744,39 @@ class Theatre { * @private */ _buildResyncData() { - let insertData = []; - for (let idx=0; idx{return a.sortidx-b.sortidx}); - return insertData; + insertData.sort((a, b) => { + return a.sortidx - b.sortidx; + }); + return insertData; } /** @@ -812,32 +793,29 @@ class Theatre { * @private */ _sendResyncRequest(type) { - if (Theatre.DEBUG) console.log("Sending RESYNC Request ", type); + if (Theatre.DEBUG) console.log("Sending RESYNC Request ", type); // If there's a GM, request to resync from them - let data = {}; + let data = {}; if (type == "players" && game.user.isGM) { - data.insertdata = this._buildResyncData(); - data.narrator = this.isNarratorActive; + data.insertdata = this._buildResyncData(); + data.narrator = this.isNarratorActive; } - game.socket.emit(Theatre.SOCKET, - { - senderId: game.user.id, - type: "reqresync", - subtype: type || "any", - data: data - }, - ); + game.socket.emit(Theatre.SOCKET, { + senderId: game.user.id, + type: "reqresync", + subtype: type || "any", + data: data, + }); if (type != "players") { - this.resync.type = type; - this.resync.timeoutId = window.setTimeout(()=>{ - console.log("RESYNC REQUEST TIMEOUT"); - this.resync.timeoutId = null; - },5000); + this.resync.type = type; + this.resync.timeoutId = window.setTimeout(() => { + console.log("RESYNC REQUEST TIMEOUT"); + this.resync.timeoutId = null; + }, 5000); } - } /** @@ -850,183 +828,179 @@ class Theatre { * @param type (String) : The type of resync request, can either be "players" or "gm" * @param senderId (String) : The userId of the player requesting the resync event * @param data (Object) : The data payload of the resync request. If the type is - * "players" then chain process this as a resync event rather - * than a request. + * "players" then chain process this as a resync event rather + * than a request. * * @private */ _processResyncRequest(type, senderId, data) { - if (Theatre.DEBUG) console.log("Processing resync request"); + if (Theatre.DEBUG) console.log("Processing resync request"); // If the dock is not active, no need to send anything if (type == "any" && this.dockActive <= 0 && !this.isNarratorActive) { - console.log("OUR DOCK IS NOT ACTIVE, Not responding to reqresync") + console.log("OUR DOCK IS NOT ACTIVE, Not responding to reqresync"); return; } else if (type == "gm" && !game.user.isGM) { - return; + return; } else if (type == "players") { // clear our theatre - for (let insert of this.portraitDocks) - this.removeInsertById(insert.imgId,true); + for (let insert of this.portraitDocks) this.removeInsertById(insert.imgId, true); // process this as if it were a resyncevent - this.resync.timeoutId = 1; - this._processResyncEvent("gm",senderId,{ - targetid : game.user.id, - insertdata : data.insertdata, - narrator : data.narrator - }); + this.resync.timeoutId = 1; + this._processResyncEvent("gm", senderId, { + targetid: game.user.id, + insertdata: data.insertdata, + narrator: data.narrator, + }); } else { - this._sendResyncEvent(senderId); + this._sendResyncEvent(senderId); } } - - /** * Process a resync event, and if valid, unload all inserts, prepare assets for inserts to inject, - * and inject them. + * and inject them. * * @param type (String) : The type of the resync event, can either be "player" or "gm" indicating - * the permission level of the sender (only player or gm atm). - * @param senderId (String) : The userId of the player whom sent the resync event. + * the permission level of the sender (only player or gm atm). + * @param senderId (String) : The userId of the player whom sent the resync event. * @param data (Object) : The data of the resync Event which will contain the - * information of the inserts we need to load in. + * information of the inserts we need to load in. * @private */ _processResyncEvent(type, senderId, data) { - if (Theatre.DEBUG) console.log("Processing resync event %s :",type,data,game.users.get(senderId)); + if (Theatre.DEBUG) console.log("Processing resync event %s :", type, data, game.users.get(senderId)); // if we're resyncing and it's us that's the target - if (this.resync.timeoutId && (data.targetid == game.user.id || ("gm" == this.resync.type == type))) { + if (this.resync.timeoutId && (data.targetid == game.user.id || ("gm" == this.resync.type) == type)) { // drop all other resync responses, first come, first process - window.clearTimeout(this.resync.timeoutId); - this.resync.timeoutId = null; + window.clearTimeout(this.resync.timeoutId); + this.resync.timeoutId = null; // clear our theatre - for (let insert of this.portraitDocks) - this.removeInsertById(insert.imgId,true); + for (let insert of this.portraitDocks) this.removeInsertById(insert.imgId, true); - if (type == "gm") - ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.ResyncGM")); - else - ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.ResyncPlayer") + game.users.get(senderId).data.name); + if (type == "gm") ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.ResyncGM")); + else ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.ResyncPlayer") + game.users.get(senderId).data.name); - let theatreId,insert,port,actorId,actor,params; - let toInject = []; + let theatreId, insert, port, actorId, actor, params; + let toInject = []; for (let dat of data.insertdata) { theatreId = dat.insertid; - actorId = theatreId.replace("theatre-",""); - params = this._getInsertParamsFromActorId(actorId); + actorId = theatreId.replace("theatre-", ""); + params = this._getInsertParamsFromActorId(actorId); if (!params) continue; - if (Theatre.DEBUG) console.log("params + emotions: ",params,dat.emotions); - toInject.push({params: params, emotions: dat.emotions}); + if (Theatre.DEBUG) console.log("params + emotions: ", params, dat.emotions); + toInject.push({ params: params, emotions: dat.emotions }); } // let the clearing animation complete - window.setTimeout(()=>{ - // stage all inserts; - let ids = data.insertdata.map(e => e.insertid); + window.setTimeout(() => { + // stage all inserts; + let ids = data.insertdata.map((e) => e.insertid); //once all inserts are staged, start our injections - this.stageAllInserts(ids,(loader,resources)=>{ + this.stageAllInserts(ids, (loader, resources) => { // due to the 'dual dock' mode and how it combines, we can't just push the reverse // if we want to preserve order if (toInject.length >= 2) { this.injectLeftPortrait( - toInject[toInject.length-2].params.src, - toInject[toInject.length-2].params.name, - toInject[toInject.length-2].params.imgId, - toInject[toInject.length-2].params.optalign, - { - emote : toInject[toInject.length-2].emotions.emote, - textFlyin : toInject[toInject.length-2].emotions.textflyin, - textStanding : toInject[toInject.length-2].emotions.textstanding, - textFont : toInject[toInject.length-2].emotions.textfont, - textSize : toInject[toInject.length-2].emotions.textsize, - textColor : toInject[toInject.length-2].emotions.textcolor - }, - true); + toInject[toInject.length - 2].params.src, + toInject[toInject.length - 2].params.name, + toInject[toInject.length - 2].params.imgId, + toInject[toInject.length - 2].params.optalign, + { + emote: toInject[toInject.length - 2].emotions.emote, + textFlyin: toInject[toInject.length - 2].emotions.textflyin, + textStanding: toInject[toInject.length - 2].emotions.textstanding, + textFont: toInject[toInject.length - 2].emotions.textfont, + textSize: toInject[toInject.length - 2].emotions.textsize, + textColor: toInject[toInject.length - 2].emotions.textcolor, + }, + true + ); this.injectLeftPortrait( - toInject[toInject.length-1].params.src, - toInject[toInject.length-1].params.name, - toInject[toInject.length-1].params.imgId, - toInject[toInject.length-1].params.optalign, + toInject[toInject.length - 1].params.src, + toInject[toInject.length - 1].params.name, + toInject[toInject.length - 1].params.imgId, + toInject[toInject.length - 1].params.optalign, + { + emote: toInject[toInject.length - 1].emotions.emote, + textFlyin: toInject[toInject.length - 1].emotions.textflyin, + textStanding: toInject[toInject.length - 1].emotions.textstanding, + textFont: toInject[toInject.length - 1].emotions.textfont, + textSize: toInject[toInject.length - 1].emotions.textsize, + textColor: toInject[toInject.length - 1].emotions.textcolor, + }, + true + ); + for (let idx = toInject.length - 3; idx >= 0; --idx) + this.injectLeftPortrait( + toInject[idx].params.src, + toInject[idx].params.name, + toInject[idx].params.imgId, + toInject[idx].params.optalign, { - emote : toInject[toInject.length-1].emotions.emote, - textFlyin : toInject[toInject.length-1].emotions.textflyin, - textStanding : toInject[toInject.length-1].emotions.textstanding, - textFont : toInject[toInject.length-1].emotions.textfont, - textSize : toInject[toInject.length-1].emotions.textsize, - textColor : toInject[toInject.length-1].emotions.textcolor + emote: toInject[idx].emotions.emote, + textFlyin: toInject[idx].emotions.textflyin, + textStanding: toInject[idx].emotions.textstanding, + textFont: toInject[idx].emotions.textfont, + textSize: toInject[idx].emotions.textsize, + textColor: toInject[idx].emotions.textcolor, }, - true); - for (let idx=toInject.length-3; idx>=0; --idx) - this.injectLeftPortrait( - toInject[idx].params.src, - toInject[idx].params.name, - toInject[idx].params.imgId, - toInject[idx].params.optalign, - { - emote : toInject[idx].emotions.emote, - textFlyin : toInject[idx].emotions.textflyin, - textStanding : toInject[idx].emotions.textstanding, - textFont : toInject[idx].emotions.textfont, - textSize : toInject[idx].emotions.textsize, - textColor : toInject[idx].emotions.textcolor - }, - true); + true + ); } else if (toInject.length == 1) { this.injectLeftPortrait( - toInject[0].params.src, - toInject[0].params.name, - toInject[0].params.imgId, - toInject[0].params.optalign, - { - emote : toInject[0].emotions.emote, - textFlyin : toInject[0].emotions.textflyin, - textStanding : toInject[0].emotions.textstanding, - textFont : toInject[0].emotions.textfont, - textSize : toInject[0].emotions.textsize, - textColor : toInject[0].emotions.textcolor - }, - true); + toInject[0].params.src, + toInject[0].params.name, + toInject[0].params.imgId, + toInject[0].params.optalign, + { + emote: toInject[0].emotions.emote, + textFlyin: toInject[0].emotions.textflyin, + textStanding: toInject[0].emotions.textstanding, + textFont: toInject[0].emotions.textfont, + textSize: toInject[0].emotions.textsize, + textColor: toInject[0].emotions.textcolor, + }, + true + ); } // finally apply positioning for 3n total run speed - window.setTimeout(()=>{ + window.setTimeout(() => { for (let dat of data.insertdata) { - insert = this.getInsertById(dat.insertid); - //console.log("attempting to apply position to ",insert,dat.insertid,dat); + insert = this.getInsertById(dat.insertid); + //console.log("attempting to apply position to ",insert,dat.insertid,dat); if (insert) { - if (Theatre.DEBUG) console.log("insert active post resync add, appying position"); + if (Theatre.DEBUG) console.log("insert active post resync add, appying position"); // apply mirror state /* if (Boolean(dat.position.mirror) != insert.mirrored) this._mirrorInsert(port,true); */ - if (Theatre.DEBUG) console.log("Mirror ? %s : %s",dat.position.mirror, insert.mirrored); + if (Theatre.DEBUG) console.log("Mirror ? %s : %s", dat.position.mirror, insert.mirrored); if (Boolean(dat.position.mirror) != insert.mirrored) { - if (Theatre.DEBUG) console.log("no match!"); - insert.mirrored = Boolean(dat.position.mirror); + if (Theatre.DEBUG) console.log("no match!"); + insert.mirrored = Boolean(dat.position.mirror); } // apply positioning data - insert.portraitContainer.scale.x = (insert.mirrored ? -1 : 1); - insert.portraitContainer.x = dat.position.x; - insert.portraitContainer.y = dat.position.y; + insert.portraitContainer.scale.x = insert.mirrored ? -1 : 1; + insert.portraitContainer.x = dat.position.x; + insert.portraitContainer.y = dat.position.y; // apply texyflyin/textstanding data - insert.textFlyin = dat.emotions.textflyin; - insert.textStanding = dat.emotions.textstanding; - insert.textFont = dat.emotions.textfont; - insert.textSize = dat.emotions.textsize; - insert.textColor = dat.emotions.textcolor; + insert.textFlyin = dat.emotions.textflyin; + insert.textStanding = dat.emotions.textstanding; + insert.textFont = dat.emotions.textfont; + insert.textSize = dat.emotions.textsize; + insert.textColor = dat.emotions.textcolor; } } // apply Narrator bar last - this.toggleNarratorBar(data.narrator); - },1000); - }); - },1600); - + this.toggleNarratorBar(data.narrator); + }, 1000); + }); + }, 1600); } } - /** * Process a scene update payload * @@ -1055,202 +1029,202 @@ class Theatre { * @private */ _processSceneEvent(senderId, type, data) { - if (Theatre.DEBUG) console.log("Processing scene event %s",type,data); - let insert,actorId,params,emote,port,emotions,resName,app,insertEmote,render; + if (Theatre.DEBUG) console.log("Processing scene event %s", type, data); + let insert, actorId, params, emote, port, emotions, resName, app, insertEmote, render; switch (type) { case "enterscene": - if (Theatre.DEBUG) console.log("enterscene: aid:%s",actorId); - actorId = data.insertid.replace("theatre-",""); - params = this._getInsertParamsFromActorId(actorId); - emotions = (data.emotions ? data.emotions : { - emote: null, - textFlying: null, - textStanding: null, - textFont: null, - textSize: null, - textColor: null - }); + if (Theatre.DEBUG) console.log("enterscene: aid:%s", actorId); + actorId = data.insertid.replace("theatre-", ""); + params = this._getInsertParamsFromActorId(actorId); + emotions = data.emotions + ? data.emotions + : { + emote: null, + textFlying: null, + textStanding: null, + textFont: null, + textSize: null, + textColor: null, + }; if (!params) return; - if (Theatre.DEBUG) console.log("params: ",params); - if (data.isleft) - this.injectLeftPortrait(params.src,params.name,params.imgId,params.optalign,emotions,true); - else - this.injectRightPortrait(params.src,params.name,params.imgId,params.optalign,emotions,true); + if (Theatre.DEBUG) console.log("params: ", params); + if (data.isleft) this.injectLeftPortrait(params.src, params.name, params.imgId, params.optalign, emotions, true); + else this.injectRightPortrait(params.src, params.name, params.imgId, params.optalign, emotions, true); break; case "exitscene": - if (Theatre.DEBUG) console.log("exitscene: tid:%s",data.insertid); - this.removeInsertById(data.insertid,true); + if (Theatre.DEBUG) console.log("exitscene: tid:%s", data.insertid); + this.removeInsertById(data.insertid, true); break; case "positionupdate": - if (Theatre.DEBUG) console.log("positionupdate: tid:%s",data.insertid); - insert = this.getInsertById(data.insertid); + if (Theatre.DEBUG) console.log("positionupdate: tid:%s", data.insertid); + insert = this.getInsertById(data.insertid); if (insert) { // apply mirror state - if (Theatre.DEBUG) console.log("mirroring desired: %s , current mirror %s",data.position.mirror,insert.mirrored); - if (Boolean(data.position.mirror) != insert.mirrored) - insert.mirrored = data.position.mirror; + if (Theatre.DEBUG) console.log("mirroring desired: %s , current mirror %s", data.position.mirror, insert.mirrored); + if (Boolean(data.position.mirror) != insert.mirrored) insert.mirrored = data.position.mirror; // apply positioning data - //insert.portraitContainer.x = data.position.x; - //insert.portraitContainer.y = data.position.y; - let tweenId = "portraitMove"; - let tween = TweenMax.to(insert.portraitContainer,0.5,{ - pixi:{scaleX:(data.position.mirror ? -1 : 1) ,x: data.position.x, y: data.position.y}, + //insert.portraitContainer.x = data.position.x; + //insert.portraitContainer.y = data.position.y; + let tweenId = "portraitMove"; + let tween = TweenMax.to(insert.portraitContainer, 0.5, { + pixi: { scaleX: data.position.mirror ? -1 : 1, x: data.position.x, y: data.position.y }, ease: Power3.easeOut, - onComplete: function(ctx,imgId,tweenId) { + onComplete: function (ctx, imgId, tweenId) { // decrement the rendering accumulator - ctx._removeDockTween(imgId,this,tweenId); + ctx._removeDockTween(imgId, this, tweenId); // remove our own reference from the dockContainer tweens }, - onCompleteParams: [this,insert.imgId,tweenId] - }); - this._addDockTween(insert.imgId,tween,tweenId); + onCompleteParams: [this, insert.imgId, tweenId], + }); + this._addDockTween(insert.imgId, tween, tweenId); } break; case "push": - if (Theatre.DEBUG) console.log("insertpush: tid:%s",data.insertid); - this.pushInsertById(data.insertid,data.tofront,true); - break; + if (Theatre.DEBUG) console.log("insertpush: tid:%s", data.insertid); + this.pushInsertById(data.insertid, data.tofront, true); + break; case "swap": - if (Theatre.DEBUG) console.log("insertswap: tid1:%s tid2:%s",data.insertid1,data.insertid2); - this.swapInsertsById(data.insertid1,data.insertid2,true); - break; + if (Theatre.DEBUG) console.log("insertswap: tid1:%s tid2:%s", data.insertid1, data.insertid2); + this.swapInsertsById(data.insertid1, data.insertid2, true); + break; case "move": - if (Theatre.DEBUG) console.log("insertmove: tid1:%s tid2:%s",data.insertid1,data.insertid2); - this.moveInsertById(data.insertid1,data.insertid2,true); - break; + if (Theatre.DEBUG) console.log("insertmove: tid1:%s tid2:%s", data.insertid1, data.insertid2); + this.moveInsertById(data.insertid1, data.insertid2, true); + break; case "emote": - if (Theatre.DEBUG) console.log("emote:",data); + if (Theatre.DEBUG) console.log("emote:", data); emote = data.emotions.emote; - let textFlyin = data.emotions.textflyin; - let textStanding = data.emotions.textstanding; - let textFont = data.emotions.textfont; - let textSize = data.emotions.textsize; - let textColor = data.emotions.textcolor; - this.setUserEmote(senderId,data.insertid,"emote",emote,true); - this.setUserEmote(senderId,data.insertid,"textflyin",textFlyin,true); - this.setUserEmote(senderId,data.insertid,"textstanding",textStanding,true); - this.setUserEmote(senderId,data.insertid,"textfont",textFont,true); - this.setUserEmote(senderId,data.insertid,"textsize",textSize,true); - this.setUserEmote(senderId,data.insertid,"textcolor",textColor,true); - if (data.insertid == this.speakingAs) - this.renderEmoteMenu(); - break; + let textFlyin = data.emotions.textflyin; + let textStanding = data.emotions.textstanding; + let textFont = data.emotions.textfont; + let textSize = data.emotions.textsize; + let textColor = data.emotions.textcolor; + this.setUserEmote(senderId, data.insertid, "emote", emote, true); + this.setUserEmote(senderId, data.insertid, "textflyin", textFlyin, true); + this.setUserEmote(senderId, data.insertid, "textstanding", textStanding, true); + this.setUserEmote(senderId, data.insertid, "textfont", textFont, true); + this.setUserEmote(senderId, data.insertid, "textsize", textSize, true); + this.setUserEmote(senderId, data.insertid, "textcolor", textColor, true); + if (data.insertid == this.speakingAs) this.renderEmoteMenu(); + break; case "addtexture": - if (Theatre.DEBUG) console.log("texturereplace:",data); - insert = this.getInsertById(data.insertid); - actorId = data.insertid.replace("theatre-",""); - params = this._getInsertParamsFromActorId(actorId); - if (!params) return; - - app = this.pixiCTX; - insertEmote = this._getEmoteFromInsert(insert); - render = false; - - if (insertEmote == data.emote) - render = true; - else if (!data.emote) - render = true; - - this._AddTextureResource(data.imgsrc, data.resname, data.insertid, data.emote, (loader,resources)=>{ - // if oure emote is active and we're replacing the emote texture, or base is active, and we're replacing the base texture - - if (Theatre.DEBUG) console.log("add replacement complete! ",resources[data.resname],insertEmote,data.emote,render); - if (render && app && insert && insert.dockContainer) { - if (Theatre.DEBUG) console.log("RE-RENDERING with NEW texture resource %s : %s",data.resname,data.imgsrc); - - // bubble up dataum from the update - insert.optAlign = params.optalign; - insert.name = params.name; - insert.label.text = params.name; - - this._clearPortraitContainer(data.insertid); - this._setupPortraitContainer(data.insertid,insert.optAlign,data.resname,resources); - // re-attach label + typingBubble - insert.dockContainer.addChild(insert.label); - insert.dockContainer.addChild(insert.typingBubble); - - this._repositionInsertElements(insert); - - if (data.insertid == this.speakingAs); - this.renderEmoteMenu(); - if (!this.rendering) - this._renderTheatre(performance.now()); - } - },true); - break; + if (Theatre.DEBUG) console.log("texturereplace:", data); + insert = this.getInsertById(data.insertid); + actorId = data.insertid.replace("theatre-", ""); + params = this._getInsertParamsFromActorId(actorId); + if (!params) return; + + app = this.pixiCTX; + insertEmote = this._getEmoteFromInsert(insert); + render = false; + + if (insertEmote == data.emote) render = true; + else if (!data.emote) render = true; + + this._AddTextureResource( + data.imgsrc, + data.resname, + data.insertid, + data.emote, + (loader, resources) => { + // if oure emote is active and we're replacing the emote texture, or base is active, and we're replacing the base texture + + if (Theatre.DEBUG) console.log("add replacement complete! ", resources[data.resname], insertEmote, data.emote, render); + if (render && app && insert && insert.dockContainer) { + if (Theatre.DEBUG) console.log("RE-RENDERING with NEW texture resource %s : %s", data.resname, data.imgsrc); + + // bubble up dataum from the update + insert.optAlign = params.optalign; + insert.name = params.name; + insert.label.text = params.name; + + this._clearPortraitContainer(data.insertid); + this._setupPortraitContainer(data.insertid, insert.optAlign, data.resname, resources); + // re-attach label + typingBubble + insert.dockContainer.addChild(insert.label); + insert.dockContainer.addChild(insert.typingBubble); + + this._repositionInsertElements(insert); + + if (data.insertid == this.speakingAs); + this.renderEmoteMenu(); + if (!this.rendering) this._renderTheatre(performance.now()); + } + }, + true + ); + break; case "addalltextures": - if (Theatre.DEBUG) console.log("textureallreplace:",data); - insert = this.getInsertById(data.insertid); - actorId = data.insertid.replace("theatre-",""); - params = this._getInsertParamsFromActorId(actorId); - if (!params) return; - - app = this.pixiCTX; - insertEmote = this._getEmoteFromInsert(insert); - render = false; - - if (insertEmote == data.emote) - render = true; - else if (!data.emote) - render = true; - - this._AddAllTextureResources(data.imgsrcs, data.insertid, data.emote, data.eresname, (loader,resources)=>{ - // if oure emote is active and we're replacing the emote texture, or base is active, and we're replacing the base texture - - if (Theatre.DEBUG) console.log("add all textures complete! ",data.emote,data.eresname,params.emotes[data.emote]); - if (render - && app - && insert - && insert.dockContainer - && data.eresname) { - if (Theatre.DEBUG) console.log("RE-RENDERING with NEW texture resource %s",data.eresname); - - // bubble up dataum from the update - insert.optAlign = params.optalign; - insert.name = params.name; - insert.label.text = params.name; - - this._clearPortraitContainer(data.insertid); - this._setupPortraitContainer(data.insertid,insert.optAlign,data.eresname,resources); - // re-attach label + typingBubble - insert.dockContainer.addChild(insert.label); - insert.dockContainer.addChild(insert.typingBubble); - - this._repositionInsertElements(insert); - - if (data.insertid == this.speakingAs); - this.renderEmoteMenu(); - if (!this.rendering) - this._renderTheatre(performance.now()); - } - },true); - - break; + if (Theatre.DEBUG) console.log("textureallreplace:", data); + insert = this.getInsertById(data.insertid); + actorId = data.insertid.replace("theatre-", ""); + params = this._getInsertParamsFromActorId(actorId); + if (!params) return; + + app = this.pixiCTX; + insertEmote = this._getEmoteFromInsert(insert); + render = false; + + if (insertEmote == data.emote) render = true; + else if (!data.emote) render = true; + + this._AddAllTextureResources( + data.imgsrcs, + data.insertid, + data.emote, + data.eresname, + (loader, resources) => { + // if oure emote is active and we're replacing the emote texture, or base is active, and we're replacing the base texture + + if (Theatre.DEBUG) console.log("add all textures complete! ", data.emote, data.eresname, params.emotes[data.emote]); + if (render && app && insert && insert.dockContainer && data.eresname) { + if (Theatre.DEBUG) console.log("RE-RENDERING with NEW texture resource %s", data.eresname); + + // bubble up dataum from the update + insert.optAlign = params.optalign; + insert.name = params.name; + insert.label.text = params.name; + + this._clearPortraitContainer(data.insertid); + this._setupPortraitContainer(data.insertid, insert.optAlign, data.eresname, resources); + // re-attach label + typingBubble + insert.dockContainer.addChild(insert.label); + insert.dockContainer.addChild(insert.typingBubble); + + this._repositionInsertElements(insert); + + if (data.insertid == this.speakingAs); + this.renderEmoteMenu(); + if (!this.rendering) this._renderTheatre(performance.now()); + } + }, + true + ); + + break; case "stage": - if (Theatre.DEBUG) console.log("staging insert",data.insertid); - this.stageInsertById(data.insertid,true); - break; + if (Theatre.DEBUG) console.log("staging insert", data.insertid); + this.stageInsertById(data.insertid, true); + break; case "narrator": - if (Theatre.DEBUG) console.log("toggle narrator bar",data.active); - this.toggleNarratorBar(data.active,true); - break; + if (Theatre.DEBUG) console.log("toggle narrator bar", data.active); + this.toggleNarratorBar(data.active, true); + break; case "decaytext": - if (Theatre.DEBUG) console.log("decay textbox",data.insertid); - this.decayTextBoxById(data.insertid,true); - break; + if (Theatre.DEBUG) console.log("decay textbox", data.insertid); + this.decayTextBoxById(data.insertid, true); + break; case "renderinsert": - insert = this.getInsertById(data.insertid); - if (insert) - this.renderInsertById(data.insertid); - break; + insert = this.getInsertById(data.insertid); + if (insert) this.renderInsertById(data.insertid); + break; default: - console.log("UNKNOWN SCENE EVENT: %s with data: ",type,data); + console.log("UNKNOWN SCENE EVENT: %s with data: ", type, data); } } - /** * Merely getting the typing event is the payload, we just refresh the typing timout * for the given userId @@ -1264,29 +1238,27 @@ class Theatre { * * @private */ - _processTypingEvent(userId,data) { - // Possibly other things ? - this.setUserTyping(userId, data.insertid); + _processTypingEvent(userId, data) { + // Possibly other things ? + this.setUserTyping(userId, data.insertid); // emote information is a rider on this event, process it let emote = data.emotions.emote; - let textFlyin = data.emotions.textflyin; - let textStanding = data.emotions.textstanding; - let textFont = data.emotions.textfont; - let textSize = data.emotions.textsize; - let textColor = data.emotions.textcolor; - - this.setUserEmote(userId,data.insertid,"emote",emote,true); - this.setUserEmote(userId,data.insertid,"textflyin",textFlyin,true); - this.setUserEmote(userId,data.insertid,"textstanding",textStanding,true); - this.setUserEmote(userId,data.insertid,"textfont",textFont,true); - this.setUserEmote(userId,data.insertid,"textsize",textSize,true); - this.setUserEmote(userId,data.insertid,"textcolor",textColor,true); + let textFlyin = data.emotions.textflyin; + let textStanding = data.emotions.textstanding; + let textFont = data.emotions.textfont; + let textSize = data.emotions.textsize; + let textColor = data.emotions.textcolor; + + this.setUserEmote(userId, data.insertid, "emote", emote, true); + this.setUserEmote(userId, data.insertid, "textflyin", textFlyin, true); + this.setUserEmote(userId, data.insertid, "textstanding", textStanding, true); + this.setUserEmote(userId, data.insertid, "textfont", textFont, true); + this.setUserEmote(userId, data.insertid, "textsize", textSize, true); + this.setUserEmote(userId, data.insertid, "textcolor", textColor, true); // if the insertid is our speaking id, update our emote menu - if (data.insertid == this.speakingAs) - this.renderEmoteMenu(); + if (data.insertid == this.speakingAs) this.renderEmoteMenu(); } - /** * Test wither a user is typing given user id * @@ -1295,7 +1267,7 @@ class Theatre { isUserTyping(userId) { if (!this.usersTyping[userId]) return false; - return this.usersTyping[userId].timeoutId; + return this.usersTyping[userId].timeoutId; } /** @@ -1308,8 +1280,8 @@ class Theatre { * @private */ _getTextColorFromInsert(insert) { - if (!insert) return null; - return insert.textColor; + if (!insert) return null; + return insert.textColor; } /** * Get the text size given the insert @@ -1321,8 +1293,8 @@ class Theatre { * @private */ _getTextSizeFromInsert(insert) { - if (!insert) return null; - return insert.textSize; + if (!insert) return null; + return insert.textSize; } /** * Get the text font given the insert @@ -1334,8 +1306,8 @@ class Theatre { * @private */ _getTextFontFromInsert(insert) { - if (!insert) return null; - return insert.textFont; + if (!insert) return null; + return insert.textFont; } /** * Get the text fly-in animation given the insert @@ -1347,8 +1319,8 @@ class Theatre { * @private */ _getTextFlyinFromInsert(insert) { - if (!insert) return null; - return insert.textFlyin; + if (!insert) return null; + return insert.textFlyin; } /** * Get the text standing animation given the insert @@ -1360,8 +1332,8 @@ class Theatre { * @private */ _getTextStandingFromInsert(insert) { - if (!insert) return null; - return insert.textStanding; + if (!insert) return null; + return insert.textStanding; } /** @@ -1374,22 +1346,19 @@ class Theatre { * @private */ _getEmoteFromInsert(insert) { - if (!insert) return null; - if (this.isDelayEmote) - return insert.delayedOldEmote; - return insert.emote; + if (!insert) return null; + if (this.isDelayEmote) return insert.delayedOldEmote; + return insert.emote; } /** * Get the inserts which are typing based on if their users are typing */ getInsertsTyping() { - let typing = []; - for (let userId in this.usersTyping) - if (this.usersTyping[userId].theatreId) - typing.push(userId); + let typing = []; + for (let userId in this.usersTyping) if (this.usersTyping[userId].theatreId) typing.push(userId); - return typing; + return typing; } /** @@ -1402,108 +1371,105 @@ class Theatre { * @param value (String) : The value of the emote state that is being set * @param remote (Boolean) : Boolean indicating if this is a remote or local action */ - setUserEmote(userId,theatreId,subType,value,remote) { - if (!this.userEmotes[userId]) - this.userEmotes[userId] = {}; + setUserEmote(userId, theatreId, subType, value, remote) { + if (!this.userEmotes[userId]) this.userEmotes[userId] = {}; - let userEmoting = this.userEmotes[userId]; - let insert = this.getInsertById(theatreId); + let userEmoting = this.userEmotes[userId]; + let insert = this.getInsertById(theatreId); - switch(subType) { + switch (subType) { case "textfont": if (insert) { - if (value) insert.textFont = value; - else insert.textFont = null; + if (value) insert.textFont = value; + else insert.textFont = null; } else if (theatreId == Theatre.NARRATOR) { - if (value) this.theatreNarrator.setAttribute("textfont",value); - else this.theatreNarrator.removeAttribute("textfont",value); + if (value) this.theatreNarrator.setAttribute("textfont", value); + else this.theatreNarrator.removeAttribute("textfont", value); } else { - userEmoting.textFont = value; + userEmoting.textFont = value; } break; case "textsize": if (insert) { - if (value) insert.textSize = value; - else insert.textSize = null; + if (value) insert.textSize = value; + else insert.textSize = null; } else if (theatreId == Theatre.NARRATOR) { - if (value) this.theatreNarrator.setAttribute("textsize",value); - else this.theatreNarrator.removeAttribute("textsize",value); - userEmoting.textSize = value; + if (value) this.theatreNarrator.setAttribute("textsize", value); + else this.theatreNarrator.removeAttribute("textsize", value); + userEmoting.textSize = value; } else { - userEmoting.textSize = value; + userEmoting.textSize = value; } break; case "textcolor": if (insert) { - if (value) insert.textColor = value; - else insert.textColor = null; + if (value) insert.textColor = value; + else insert.textColor = null; } else if (theatreId == Theatre.NARRATOR) { - if (value) this.theatreNarrator.setAttribute("textcolor",value); - else this.theatreNarrator.removeAttribute("textcolor",value); + if (value) this.theatreNarrator.setAttribute("textcolor", value); + else this.theatreNarrator.removeAttribute("textcolor", value); } else { - userEmoting.textColor = value; + userEmoting.textColor = value; } - break; + break; case "textflyin": if (insert) { - if (value) insert.textFlyin = value; - else insert.textFlyin = null; + if (value) insert.textFlyin = value; + else insert.textFlyin = null; } else if (theatreId == Theatre.NARRATOR) { - if (value) this.theatreNarrator.setAttribute("textflyin",value); - else this.theatreNarrator.removeAttribute("textflyin",value); + if (value) this.theatreNarrator.setAttribute("textflyin", value); + else this.theatreNarrator.removeAttribute("textflyin", value); } else { - userEmoting.textFlyin = value; + userEmoting.textFlyin = value; } - break; + break; case "textstanding": if (insert) { - if (value) insert.textStanding = value; - else insert.textStanding = null; + if (value) insert.textStanding = value; + else insert.textStanding = null; } else if (theatreId == Theatre.NARRATOR) { - if (value) this.theatreNarrator.setAttribute("textstanding",value); - else this.theatreNarrator.removeAttribute("textstanding",value); + if (value) this.theatreNarrator.setAttribute("textstanding", value); + else this.theatreNarrator.removeAttribute("textstanding", value); } else { - userEmoting.textStanding = value; + userEmoting.textStanding = value; } - break; + break; case "emote": // if provided a theatreId, set that insert's emote image + effects if (insert) { // if we're delaying our emote, and ths user is us, hold off on setting it - if (this.isDelayEmote - && userId == game.user.id - && (this.delayedSentState == 0 || this.delayedSentState == 1)) { + if (this.isDelayEmote && userId == game.user.id && (this.delayedSentState == 0 || this.delayedSentState == 1)) { if (this.delayedSentState == 0) { - insert.delayedOldEmote = insert.emote; - this.delayedSentState = 1; + insert.delayedOldEmote = insert.emote; + this.delayedSentState = 1; } - if (Theatre.DEBUG) console.log("DELAYING EMOTE %s, 'showing' %s",value,insert.delayedOldEmote); + if (Theatre.DEBUG) console.log("DELAYING EMOTE %s, 'showing' %s", value, insert.delayedOldEmote); } else { - insert.delayedOldEmote = insert.emote; - this.setEmoteForInsertById(value,theatreId,remote); + insert.delayedOldEmote = insert.emote; + this.setEmoteForInsertById(value, theatreId, remote); } - if (value) insert.emote = value; - else insert.emote = null; + if (value) insert.emote = value; + else insert.emote = null; } else { - userEmoting.emote = value; + userEmoting.emote = value; } - break; + break; } // Send to socket - if (Theatre.DEBUG) console.log("SEND EMOTE PACKET %s,%s ??",this.isDelayEmote,this.delayedSentState); + if (Theatre.DEBUG) console.log("SEND EMOTE PACKET %s,%s ??", this.isDelayEmote, this.delayedSentState); if (!remote && (!this.isDelayEmote || this.delayedSentState == 2) && (insert || theatreId == Theatre.NARRATOR)) { - if (Theatre.DEBUG) console.log("SENDING EMOTE PACKET %s,%s",this.isDelayEmote,this.delayedSentState); - this._sendSceneEvent("emote",{ - insertid: (insert ? insert.imgId : Theatre.NARRATOR), + if (Theatre.DEBUG) console.log("SENDING EMOTE PACKET %s,%s", this.isDelayEmote, this.delayedSentState); + this._sendSceneEvent("emote", { + insertid: insert ? insert.imgId : Theatre.NARRATOR, emotions: { - emote: (insert ? this._getEmoteFromInsert(insert) : null), - textflyin: (insert ? this._getTextFlyinFromInsert(insert) : this.theatreNarrator.getAttribute("textflyin")), - textstanding: (insert ? this._getTextStandingFromInsert(insert) : this.theatreNarrator.getAttribute("textstanding")), - textfont: (insert ? this._getTextFontFromInsert(insert) : this.theatreNarrator.getAttribute("textfont")), - textsize: (insert ? this._getTextSizeFromInsert(insert) : this.theatreNarrator.getAttribute("textsize")), - textcolor: (insert ? this._getTextColorFromInsert(insert) : this.theatreNarrator.getAttribute("textcolor")), - } - }); + emote: insert ? this._getEmoteFromInsert(insert) : null, + textflyin: insert ? this._getTextFlyinFromInsert(insert) : this.theatreNarrator.getAttribute("textflyin"), + textstanding: insert ? this._getTextStandingFromInsert(insert) : this.theatreNarrator.getAttribute("textstanding"), + textfont: insert ? this._getTextFontFromInsert(insert) : this.theatreNarrator.getAttribute("textfont"), + textsize: insert ? this._getTextSizeFromInsert(insert) : this.theatreNarrator.getAttribute("textsize"), + textcolor: insert ? this._getTextColorFromInsert(insert) : this.theatreNarrator.getAttribute("textcolor"), + }, + }); } } @@ -1513,215 +1479,207 @@ class Theatre { * @param userId (String) : The userId of the user that is to be set as 'typing'. * @param theatreId (String) : The theatreId the user is 'typing' as. */ - setUserTyping(userId,theatreId) { - if (!this.usersTyping[userId]) - this.usersTyping[userId] = {}; + setUserTyping(userId, theatreId) { + if (!this.usersTyping[userId]) this.usersTyping[userId] = {}; - let userTyping = this.usersTyping[userId]; - if (userTyping.timeoutId) - window.clearTimeout(userTyping.timeoutId); + let userTyping = this.usersTyping[userId]; + if (userTyping.timeoutId) window.clearTimeout(userTyping.timeoutId); // clear old speakingId if it still exists if (theatreId != userTyping.theatreId) { - let insert = this.getInsertById(userTyping.theatreId); + let insert = this.getInsertById(userTyping.theatreId); // if not destroyed already if (insert && insert.portrait) { // kill tweens // hide - this._removeDockTween(insert.imgId,null,"typingAppear"); - this._removeDockTween(insert.imgId,null,"typingWiggle"); - this._removeDockTween(insert.imgId,null,"typingBounce"); + this._removeDockTween(insert.imgId, null, "typingAppear"); + this._removeDockTween(insert.imgId, null, "typingWiggle"); + this._removeDockTween(insert.imgId, null, "typingBounce"); // fade away - let oy = insert.portrait.height - - (insert.optAlign == "top" ? 0 : this.theatreBar.offsetHeight); + let oy = insert.portrait.height - (insert.optAlign == "top" ? 0 : this.theatreBar.offsetHeight); // style specific settings switch (this.settings.theatreStyle) { case "lightbox": - break; + break; case "clearbox": - oy += (insert.optAlign == "top" ? 0 : this.theatreBar.offsetHeight); - break; + oy += insert.optAlign == "top" ? 0 : this.theatreBar.offsetHeight; + break; case "mangabubble": - break; + break; case "textbox": - break; + break; default: - break; + break; } - let tweenId = "typingVanish"; - let tween = TweenMax.to(insert.typingBubble,0.2,{ - pixi:{scaleX: 0.01, scaleY: 0.01, alpha: 0, y: oy}, + let tweenId = "typingVanish"; + let tween = TweenMax.to(insert.typingBubble, 0.2, { + pixi: { scaleX: 0.01, scaleY: 0.01, alpha: 0, y: oy }, ease: Power0.easeNone, - onComplete: function(ctx,imgId,tweenId) { + onComplete: function (ctx, imgId, tweenId) { // decrement the rendering accumulator - ctx._removeDockTween(imgId,this,tweenId); - this.targets()[0].scale.x = 1; - this.targets()[0].scale.y = 1; + ctx._removeDockTween(imgId, this, tweenId); + this.targets()[0].scale.x = 1; + this.targets()[0].scale.y = 1; // remove our own reference from the dockContainer tweens }, - onCompleteParams: [this,insert.imgId,tweenId] - }); - this._addDockTween(insert.imgId,tween,tweenId); + onCompleteParams: [this, insert.imgId, tweenId], + }); + this._addDockTween(insert.imgId, tween, tweenId); - //insert.typingBubble.alpha = 0; - userTyping.theatreId = null; + //insert.typingBubble.alpha = 0; + userTyping.theatreId = null; } } if (theatreId) { - let insert = this.getInsertById(theatreId); + let insert = this.getInsertById(theatreId); // if not destroyed already if (insert && insert.portrait && !insert.tweens["typingWiggle"]) { // start tweens // show - this._removeDockTween(insert.imgId,null,"typingVanish"); + this._removeDockTween(insert.imgId, null, "typingVanish"); - let tweenId = "typingAppear"; - insert.typingBubble.scale.x = 0.01; - insert.typingBubble.scale.y = 0.01; - let tween = TweenMax.to(insert.typingBubble,0.2,{ - pixi:{scaleX: 1, scaleY: 1, alpha: 1}, + let tweenId = "typingAppear"; + insert.typingBubble.scale.x = 0.01; + insert.typingBubble.scale.y = 0.01; + let tween = TweenMax.to(insert.typingBubble, 0.2, { + pixi: { scaleX: 1, scaleY: 1, alpha: 1 }, ease: Power0.easeNone, - onComplete: function(ctx,imgId,tweenId) { + onComplete: function (ctx, imgId, tweenId) { // decrement the rendering accumulator - ctx._removeDockTween(imgId,this,tweenId); - this.targets()[0].scale.x = 1; - this.targets()[0].scale.y = 1; + ctx._removeDockTween(imgId, this, tweenId); + this.targets()[0].scale.x = 1; + this.targets()[0].scale.y = 1; // remove our own reference from the dockContainer tweens }, - onCompleteParams: [this,insert.imgId,tweenId] - }); - this._addDockTween(insert.imgId,tween,tweenId); - - tweenId = "typingWiggle"; - insert.typingBubble.rotation = 0.174533; - tween = TweenMax.to(insert.typingBubble,0.5,{ - pixi:{rotation: -10}, + onCompleteParams: [this, insert.imgId, tweenId], + }); + this._addDockTween(insert.imgId, tween, tweenId); + + tweenId = "typingWiggle"; + insert.typingBubble.rotation = 0.174533; + tween = TweenMax.to(insert.typingBubble, 0.5, { + pixi: { rotation: -10 }, ease: Power0.easeNone, repeat: -1, yoyo: true, - onComplete: function(ctx,imgId,tweenId) { + onComplete: function (ctx, imgId, tweenId) { // decrement the rendering accumulator - ctx._removeDockTween(imgId,this,tweenId); + ctx._removeDockTween(imgId, this, tweenId); // remove our own reference from the dockContainer tweens }, - onCompleteParams: [this,insert.imgId,tweenId] - }); - this._addDockTween(insert.imgId,tween,tweenId); + onCompleteParams: [this, insert.imgId, tweenId], + }); + this._addDockTween(insert.imgId, tween, tweenId); - let oy = insert.portrait.height - - (insert.optAlign == "top" ? 0 : this.theatreBar.offsetHeight) - insert.label.style.lineHeight*0.75; + let oy = insert.portrait.height - (insert.optAlign == "top" ? 0 : this.theatreBar.offsetHeight) - insert.label.style.lineHeight * 0.75; // style specific settings switch (this.settings.theatreStyle) { case "clearbox": - insert.typingBubble.y = insert.portrait.height; - oy += (insert.optAlign == "top" ? 0 : this.theatreBar.offsetHeight); - break; + insert.typingBubble.y = insert.portrait.height; + oy += insert.optAlign == "top" ? 0 : this.theatreBar.offsetHeight; + break; case "mangabubble": case "lightbox": case "textbox": default: - insert.typingBubble.y = insert.portrait.height - (insert.optAlign == "top" ? 0 : this.theatreBar.offsetHeight); - break; + insert.typingBubble.y = insert.portrait.height - (insert.optAlign == "top" ? 0 : this.theatreBar.offsetHeight); + break; } - tweenId = "typingBounce"; - tween = TweenMax.to(insert.typingBubble,0.25,{ - pixi:{y: oy}, + tweenId = "typingBounce"; + tween = TweenMax.to(insert.typingBubble, 0.25, { + pixi: { y: oy }, ease: Power3.easeOut, repeat: -1, yoyo: true, yoyoEase: Power0.easeNone, - onComplete: function(ctx,imgId,tweenId) { + onComplete: function (ctx, imgId, tweenId) { // decrement the rendering accumulator - ctx._removeDockTween(imgId,this,tweenId); - this.targets()[0].y = oy; + ctx._removeDockTween(imgId, this, tweenId); + this.targets()[0].y = oy; // remove our own reference from the dockContainer tweens }, - onCompleteParams: [this,insert.imgId,tweenId] - }); - this._addDockTween(insert.imgId,tween,tweenId); - + onCompleteParams: [this, insert.imgId, tweenId], + }); + this._addDockTween(insert.imgId, tween, tweenId); - //insert.typingBubble.alpha = 1; - userTyping.theatreId = theatreId; + //insert.typingBubble.alpha = 1; + userTyping.theatreId = theatreId; } else if (theatreId == Theatre.NARRATOR) { - userTyping.theatreId = theatreId; + userTyping.theatreId = theatreId; } } - userTyping.timeoutId = window.setTimeout(()=>{ - if (Theatre.DEBUG) console.log("%s typing timeout",userId); - this.removeUserTyping(userId); - },6000); + userTyping.timeoutId = window.setTimeout(() => { + if (Theatre.DEBUG) console.log("%s typing timeout", userId); + this.removeUserTyping(userId); + }, 6000); } - /** * set the user as no longer typing * * @param userId (String) : The userId to remove as 'typing'. */ removeUserTyping(userId) { - if (Theatre.DEBUG) console.log("removeUserTyping: ",this.usersTyping[userId]); + if (Theatre.DEBUG) console.log("removeUserTyping: ", this.usersTyping[userId]); if (!this.usersTyping[userId]) { - this.usersTyping[userId] = {}; - return; - } - if (!this.usersTyping[userId].timeoutId) + this.usersTyping[userId] = {}; return; + } + if (!this.usersTyping[userId].timeoutId) return; if (this.usersTyping[userId].theatreId) { - let insert = this.getInsertById(this.usersTyping[userId].theatreId); + let insert = this.getInsertById(this.usersTyping[userId].theatreId); // if not destroyed already if (insert) { // kill tweens // hide - this._removeDockTween(insert.imgId,null,"typingAppear"); - this._removeDockTween(insert.imgId,null,"typingWiggle"); - this._removeDockTween(insert.imgId,null,"typingBounce"); + this._removeDockTween(insert.imgId, null, "typingAppear"); + this._removeDockTween(insert.imgId, null, "typingWiggle"); + this._removeDockTween(insert.imgId, null, "typingBounce"); // fade away - let oy = insert.portrait.height - - (insert.optAlign == "top" ? 0 : this.theatreBar.offsetHeight); + let oy = insert.portrait.height - (insert.optAlign == "top" ? 0 : this.theatreBar.offsetHeight); // style specific settings switch (this.settings.theatreStyle) { case "lightbox": - break; + break; case "clearbox": - oy += (insert.optAlign == "top" ? 0 : this.theatreBar.offsetHeight); - break; + oy += insert.optAlign == "top" ? 0 : this.theatreBar.offsetHeight; + break; case "mangabubble": - break; + break; case "textbox": - break; + break; default: - break; + break; } - let tweenId = "typingVanish"; - let tween = TweenMax.to(insert.typingBubble,0.2,{ - pixi:{scaleX: 0.01, scaleY: 0.01, alpha: 0, y: oy}, + let tweenId = "typingVanish"; + let tween = TweenMax.to(insert.typingBubble, 0.2, { + pixi: { scaleX: 0.01, scaleY: 0.01, alpha: 0, y: oy }, ease: Power0.easeNone, - onComplete: function(ctx,imgId,tweenId) { + onComplete: function (ctx, imgId, tweenId) { // decrement the rendering accumulator - ctx._removeDockTween(imgId,this,tweenId); - this.targets()[0].scale.x = 1; - this.targets()[0].scale.y = 1; + ctx._removeDockTween(imgId, this, tweenId); + this.targets()[0].scale.x = 1; + this.targets()[0].scale.y = 1; // remove our own reference from the dockContainer tweens }, - onCompleteParams: [this,insert.imgId,tweenId] - }); - this._addDockTween(insert.imgId,tween,tweenId); + onCompleteParams: [this, insert.imgId, tweenId], + }); + this._addDockTween(insert.imgId, tween, tweenId); - //insert.typingBubble.alpha = 0; + //insert.typingBubble.alpha = 0; } } - if (Theatre.DEBUG) console.log("%s is no longer typing (removed)",userId); - window.clearTimeout(this.usersTyping[userId].timeoutId); - this.usersTyping[userId].timeoutId = null; + if (Theatre.DEBUG) console.log("%s is no longer typing (removed)", userId); + window.clearTimeout(this.usersTyping[userId].timeoutId); + this.usersTyping[userId].timeoutId = null; } /** @@ -1734,69 +1692,62 @@ class Theatre { * @private */ _getInsertParamsFromActorId(actorId) { - let actor = game.actors.get(actorId); + let actor = game.actors.get(actorId); if (!!!actor) { - console.log("ERROR, ACTOR %s DOES NOT EXIST!",actorId); + console.log("ERROR, ACTOR %s DOES NOT EXIST!", actorId); return null; } - actor = actor.data; - //console.log("getting params from actor: ",actor); + actor = actor.data; + //console.log("getting params from actor: ",actor); - let theatreId = `theatre-${actor._id}`; - let portrait = (actor.img ? actor.img : "icons/mystery-man.png"); - let optAlign = "top"; - let name = Theatre.getActorDisplayName(actor._id); - let emotes = {}; - let settings = {}; + let theatreId = `theatre-${actor._id}`; + let portrait = actor.img ? actor.img : "icons/mystery-man.png"; + let optAlign = "top"; + let name = Theatre.getActorDisplayName(actor._id); + let emotes = {}; + let settings = {}; // Use defaults incase the essential flag attributes are missing if (actor.flags.theatre) { - if (actor.flags.theatre.name && actor.flags.theatre.name != "") - name = actor.flags.theatre.name; - if (actor.flags.theatre.baseinsert && actor.flags.theatre.baseinsert != "") - portrait = actor.flags.theatre.baseinsert; - if (actor.flags.theatre.optalign && actor.flags.theatre.optalign != "") - optAlign = actor.flags.theatre.optalign; - if (actor.flags.theatre.emotes) - emotes = actor.flags.theatre.emotes; - if (actor.flags.theatre.settings) - settings = actor.flags.theatre.settings; + if (actor.flags.theatre.name && actor.flags.theatre.name != "") name = actor.flags.theatre.name; + if (actor.flags.theatre.baseinsert && actor.flags.theatre.baseinsert != "") portrait = actor.flags.theatre.baseinsert; + if (actor.flags.theatre.optalign && actor.flags.theatre.optalign != "") optAlign = actor.flags.theatre.optalign; + if (actor.flags.theatre.emotes) emotes = actor.flags.theatre.emotes; + if (actor.flags.theatre.settings) settings = actor.flags.theatre.settings; } return { - src: portrait, - name: name, - optalign: optAlign, - imgId: theatreId, + src: portrait, + name: name, + optalign: optAlign, + imgId: theatreId, emotes: emotes, - settings: settings - }; - + settings: settings, + }; } /** * Determine if the default animations are disabled given a theatreId * * @param theatreId (String) : The theatreId who's theatre properties to - * test for if the default animations are disabled. + * test for if the default animations are disabled. * * @return (Boolean) : True if disabled, false if not, null if the actor * does not exist */ isDefaultDisabled(theatreId) { - let actorId = theatreId.replace("theatre-",""); - let actor = game.actors.get(actorId); + let actorId = theatreId.replace("theatre-", ""); + let actor = game.actors.get(actorId); if (!!!actor) { - console.log("ERROR, ACTOR %s DOES NOT EXIST!",actorId); + console.log("ERROR, ACTOR %s DOES NOT EXIST!", actorId); return null; } - if (Theatre.DEBUG) console.log('isDefaultDisabled ',actor); + if (Theatre.DEBUG) console.log("isDefaultDisabled ", actor); - if (actor.data.flags.theatre && actor.data.flags.theatre.disabledefault) - return true; - return false; + if (actor.data.flags.theatre && actor.data.flags.theatre.disabledefault) return true; + return false; } /** @@ -1806,23 +1757,21 @@ class Theatre { * @params theatreId (String) : The theatreId of insert to check. * * @return (Boolean) : True if the userId owns the actor, False otherwise - * including if the actor for the theatreId does not exist. + * including if the actor for the theatreId does not exist. */ - isActorOwner(userId,theatreId) { - let user = game.users.get(userId); - if (user.isGM) return true; - let actorId = theatreId.replace("theatre-",""); - let actor = game.actors.get(actorId); + isActorOwner(userId, theatreId) { + let user = game.users.get(userId); + if (user.isGM) return true; + let actorId = theatreId.replace("theatre-", ""); + let actor = game.actors.get(actorId); if (!!!actor) { - console.log("ERROR, ACTOR %s DOES NOT EXIST!",actorId); + console.log("ERROR, ACTOR %s DOES NOT EXIST!", actorId); return false; } - actor = actor.data; - if ((actor.permission[userId] && actor.permission[userId] >= 3) - || (actor.permission["default"] && actor.permission["default"] >= 3)) - return true; - return false; + actor = actor.data; + if ((actor.permission[userId] && actor.permission[userId] >= 3) || (actor.permission["default"] && actor.permission["default"] >= 3)) return true; + return false; } /** @@ -1833,27 +1782,25 @@ class Theatre { * @return (Boolean) : True if the insert is player controlled, False otherwise */ isPlayerOwned(theatreId) { - if (game.user.isGM) return true; - let actorId = theatreId.replace("theatre-",""); - let actor = game.actors.get(actorId); + if (game.user.isGM) return true; + let actorId = theatreId.replace("theatre-", ""); + let actor = game.actors.get(actorId); let user; if (!!!actor) { - console.log("ERROR, ACTOR %s DOES NOT EXIST!",actorId); + console.log("ERROR, ACTOR %s DOES NOT EXIST!", actorId); return; } - actor = actor.data; + actor = actor.data; for (let perm in actor.permission) { if (perm != "default") { - user = game.users.get(perm); - if (!user.isGM) - return true; + user = game.users.get(perm); + if (!user.isGM) return true; } else { - if (actor.permission[perm] >=1) - return true; + if (actor.permission[perm] >= 1) return true; } } - return false; + return false; } /** @@ -1863,68 +1810,63 @@ class Theatre { * @params id (String) : The theatreId of the insert to render. */ renderInsertById(id) { - let insert = this.getInsertById(id); - let actorId = id.replace("theatre-",""); + let insert = this.getInsertById(id); + let actorId = id.replace("theatre-", ""); let resName = "icons/myster-man.png"; - let params = this._getInsertParamsFromActorId(actorId); - if (!insert || !params) return; + let params = this._getInsertParamsFromActorId(actorId); + if (!insert || !params) return; - if (insert.emote - && params.emotes[insert.emote].insert - && params.emotes[insert.emote].insert != "") - resName = params.emotes[insert.emote].insert; - else - resName = params.src; + if (insert.emote && params.emotes[insert.emote].insert && params.emotes[insert.emote].insert != "") resName = params.emotes[insert.emote].insert; + else resName = params.src; // bubble up dataum from the update insert.optAlign = params.optalign; - insert.name = params.name; - insert.label.text = params.name; + insert.name = params.name; + insert.label.text = params.name; - this._clearPortraitContainer(id); - this._setupPortraitContainer(id,params.optalign,resName,PIXI.Loader.shared.resources); + this._clearPortraitContainer(id); + this._setupPortraitContainer(id, params.optalign, resName, PIXI.Loader.shared.resources); // re attach label + typing bubble - insert.dockContainer.addChild(insert.label); - insert.dockContainer.addChild(insert.typingBubble); + insert.dockContainer.addChild(insert.label); + insert.dockContainer.addChild(insert.typingBubble); - this._repositionInsertElements(insert); + this._repositionInsertElements(insert); - if (!this.rendering) - this._renderTheatre(performance.now()); + if (!this.rendering) this._renderTheatre(performance.now()); } /** * Initialize the tooltip canvas which renders previews for the emote menu * - * @return (HTMLElement) : The canvas HTMLElement of the PIXI canvas created, or - * null if unsuccessful. + * @return (HTMLElement) : The canvas HTMLElement of the PIXI canvas created, or + * null if unsuccessful. * @private */ _initTheatreToolTip() { - let app = new PIXI.Application({width: 140, height: 140, transparent: true, antialias: true}); - let canvas = app.view; + let app = new PIXI.Application({ width: 140, height: 140, transparent: true, antialias: true }); + let canvas = app.view; if (!canvas) { console.log("FAILED TO INITILIZE TOOLTIP CANVAS!"); - return null; + return null; } - let holder = document.createElement("div"); - KHelpers.addClass(holder,"theatre-tooltip"); - KHelpers.addClass(holder,"app"); - holder.appendChild(canvas); + let holder = document.createElement("div"); + KHelpers.addClass(holder, "theatre-tooltip"); + KHelpers.addClass(holder, "app"); + holder.appendChild(canvas); // turn off ticker - app.ticker.autoStart = false; - app.ticker.stop(); + app.ticker.autoStart = false; + app.ticker.stop(); - this.pixiToolTipCTX = app; + this.pixiToolTipCTX = app; // hide - //holder.style.display = "none"; - holder.style.opacity = 0; + //holder.style.display = "none"; + holder.style.opacity = 0; - return holder; + return holder; } /** @@ -1933,81 +1875,80 @@ class Theatre { * * @params theatreId (String) : The theatreId of the insert to display in * the theatre tool tip. - * @params emote (String) : The emote of the theatreId to get for dispay - * in the theatre tool tip. + * @params emote (String) : The emote of the theatreId to get for dispay + * in the theatre tool tip. */ - configureTheatreToolTip(theatreId,emote) { - if (!theatreId || theatreId == Theatre.NARRATOR) return; + configureTheatreToolTip(theatreId, emote) { + if (!theatreId || theatreId == Theatre.NARRATOR) return; - let actorId = theatreId.replace("theatre-",""); - let params = this._getInsertParamsFromActorId(actorId); - let resources = PIXI.Loader.shared.resources; + let actorId = theatreId.replace("theatre-", ""); + let params = this._getInsertParamsFromActorId(actorId); + let resources = PIXI.Loader.shared.resources; if (!params) { - console.log("ERROR actor no longer exists for %s",theatreId); - return; + console.log("ERROR actor no longer exists for %s", theatreId); + return; } - let resName = (emote && params.emotes[emote] && params.emotes[emote].insert ? params.emotes[emote].insert : params.src); + let resName = emote && params.emotes[emote] && params.emotes[emote].insert ? params.emotes[emote].insert : params.src; if (!resources[resName] || !resources[resName].texture) { - console.log("ERROR could not load texture (for tooltip) %s",resName,resources); - return; + console.log("ERROR could not load texture (for tooltip) %s", resName, resources); + return; } - let app = this.pixiToolTipCTX; + let app = this.pixiToolTipCTX; // clear canvas - for (let idx=app.stage.children.length-1; idx >= 0; --idx) { - let child = app.stage.children[idx]; - child.destroy(); - //app.stage.removeChildAt(idx); + for (let idx = app.stage.children.length - 1; idx >= 0; --idx) { + let child = app.stage.children[idx]; + child.destroy(); + //app.stage.removeChildAt(idx); } - - let sprite = new PIXI.Sprite(resources[resName].texture); - let portWidth = resources[resName].texture.width; - let portHeight = resources[resName].texture.height; - let maxSide = Math.max(portWidth,portHeight); - let scaledWidth,scaledHeight,ratio; + let sprite = new PIXI.Sprite(resources[resName].texture); + let portWidth = resources[resName].texture.width; + let portHeight = resources[resName].texture.height; + let maxSide = Math.max(portWidth, portHeight); + let scaledWidth, scaledHeight, ratio; if (maxSide == portWidth) { // scale portWidth to 200px, assign height as a fraction - scaledWidth = 140; - scaledHeight = portHeight * 140 / portWidth; - ratio = scaledHeight/portHeight; + scaledWidth = 140; + scaledHeight = (portHeight * 140) / portWidth; + ratio = scaledHeight / portHeight; app.stage.width = scaledWidth; - app.stage.height = scaledHeight; + app.stage.height = scaledHeight; - app.stage.addChild(sprite); - app.stage.scale.x = ratio*2; - app.stage.scale.y = ratio*2; - app.stage.y = 70 - (portHeight*ratio)/2; + app.stage.addChild(sprite); + app.stage.scale.x = ratio * 2; + app.stage.scale.y = ratio * 2; + app.stage.y = 70 - (portHeight * ratio) / 2; } else { // scale portHeight to 200px, assign width as a fraction - scaledHeight = 140; - scaledWidth = portWidth * 140 / portHeight; - ratio = scaledWidth/portWidth; + scaledHeight = 140; + scaledWidth = (portWidth * 140) / portHeight; + ratio = scaledWidth / portWidth; app.stage.width = scaledWidth; - app.stage.height = scaledHeight; + app.stage.height = scaledHeight; - app.stage.addChild(sprite); - app.stage.scale.x = ratio*2; - app.stage.scale.y = ratio*2; - app.stage.x = 70 - (portWidth*ratio*2)/2; + app.stage.addChild(sprite); + app.stage.scale.x = ratio * 2; + app.stage.scale.y = ratio * 2; + app.stage.x = 70 - (portWidth * ratio * 2) / 2; } // adjust dockContainer + portraitContainer dimensions to fit the image - //app.stage.y = portHeight*ratio/2; + //app.stage.y = portHeight*ratio/2; // set sprite initial coordinates + state - sprite.x = 0; - sprite.y = 0; - - //console.log("Tooltip Portrait loaded with w:%s h:%s scale:%s",portWidth,portHeight,ratio,sprite); + sprite.x = 0; + sprite.y = 0; + + //console.log("Tooltip Portrait loaded with w:%s h:%s scale:%s",portWidth,portHeight,ratio,sprite); // render and show the tooltip - app.render(); - this.theatreToolTip.style.opacity = 1; + app.render(); + this.theatreToolTip.style.opacity = 1; // face detect /* faceapi.detectSingleFace(app.view,new faceapi.TinyFaceDetectorOptions()).then((detection)=>{ @@ -2048,12 +1989,12 @@ class Theatre { * @private */ _initFaceAPI() { - const MODEL_URL = "modules/theatre/app/weights"; + const MODEL_URL = "modules/theatre/app/weights"; - faceapi.loadSsdMobilenetv1Model(MODEL_URL); - faceapi.loadTinyFaceDetectorModel(MODEL_URL); - faceapi.loadFaceLandmarkModel(MODEL_URL); - faceapi.loadFaceRecognitionModel(MODEL_URL); + faceapi.loadSsdMobilenetv1Model(MODEL_URL); + faceapi.loadTinyFaceDetectorModel(MODEL_URL); + faceapi.loadFaceLandmarkModel(MODEL_URL); + faceapi.loadFaceRecognitionModel(MODEL_URL); } /** @@ -2062,7 +2003,7 @@ class Theatre { * that they contain. * * @return (HTMLElement) : The canvas HTMLElement of the created PIXI Canvas, - * or null if unsuccessful. + * or null if unsuccessful. * @private */ _initTheatreDockCanvas() { @@ -2070,28 +2011,27 @@ class Theatre { // no need to load in any resources as that will be done on a per-diem bases // by each container portrait - let app = new PIXI.Application({ - transparent: true, + let app = new PIXI.Application({ + transparent: true, antialias: true, - width: document.body.offsetWidth + width: document.body.offsetWidth, }); - let canvas = app.view; + let canvas = app.view; if (!canvas) { console.log("FAILED TO INITILIZE DOCK CANVAS!"); - return null; + return null; } - this.theatreDock = canvas; - this.pixiCTX = app; + this.theatreDock = canvas; + this.pixiCTX = app; // turn off ticker - app.ticker.autoStart = false; - app.ticker.stop(); - + app.ticker.autoStart = false; + app.ticker.stop(); - return canvas; + return canvas; } /** @@ -2109,24 +2049,23 @@ class Theatre { */ _renderTheatre(time) { // let the ticker update all its objects - this.pixiCTX.ticker.update(time); + this.pixiCTX.ticker.update(time); // this.pixiCTX.renderer.clear(); // PIXI.v6 does not respect transparency for clear for (let insert of this.portraitDocks) { if (insert.dockContainer) { - if (Theatre.DEBUG) this._updateTheatreDebugInfo(insert); + if (Theatre.DEBUG) this._updateTheatreDebugInfo(insert); // PIXI.v6 The renderer should not clear the canvas on rendering this.pixiCTX.renderer.render(insert.dockContainer, { clear: false }); - } - else { - console.log("INSERT HAS NO CONTAINER! _renderTheatre : HOT-EJECTING it! ",insert); - this._destroyPortraitDock(insert.imgId); + } else { + console.log("INSERT HAS NO CONTAINER! _renderTheatre : HOT-EJECTING it! ", insert); + this._destroyPortraitDock(insert.imgId); } } if (this.renderAnims > 0) { - requestAnimationFrame(this._renderTheatre.bind(this)); + requestAnimationFrame(this._renderTheatre.bind(this)); } else { - if (Theatre.DEBUG) console.log("RENDERING LOOP STOPPED"); - this.rendering = false; + if (Theatre.DEBUG) console.log("RENDERING LOOP STOPPED"); + this.rendering = false; } } @@ -2140,34 +2079,34 @@ class Theatre { * * @private */ - _addDockTween(imgId,tween,tweenId) { - let insert = this.getInsertById(imgId); + _addDockTween(imgId, tween, tweenId) { + let insert = this.getInsertById(imgId); if (!insert || !insert.dockContainer) { // if dockContainer is destroyed, destroy the tween we were trying to add - console.log("Invalid Tween for %s",imgId); - if (tween) tween.kill(); - return; + console.log("Invalid Tween for %s", imgId); + if (tween) tween.kill(); + return; } // if the tweenId exists, kill that one, and replace with the new if (insert.tweens[tweenId]) { - insert.tweens[tweenId].kill(); - this.renderAnims--; + insert.tweens[tweenId].kill(); + this.renderAnims--; } if (this.renderAnims > 0) { - this.renderAnims++; - insert.tweens[tweenId] = tween; + this.renderAnims++; + insert.tweens[tweenId] = tween; } else { // if we're somehow negative, bump to 1 - this.renderAnims = 1; - insert.tweens[tweenId] = tween; + this.renderAnims = 1; + insert.tweens[tweenId] = tween; // Kick renderer if we need to if (!this.rendering) { - if (Theatre.DEBUG) console.log("RENDERING LOOP STARTED"); - this.rendering = true; - this._renderTheatre(performance.now()); + if (Theatre.DEBUG) console.log("RENDERING LOOP STARTED"); + this.rendering = true; + this._renderTheatre(performance.now()); } } } @@ -2178,36 +2117,33 @@ class Theatre { * * @params imgId (String) : The theatreId of the tween that will have it removed. * @params tween (Object TweenMax) : The TweenMax object of the tween to be removed. - * @params tweenId (String) : The tweenId of the tween to be removed. + * @params tweenId (String) : The tweenId of the tween to be removed. * * @private */ - _removeDockTween(imgId,tween,tweenId) { - if (tween) tween.kill(); + _removeDockTween(imgId, tween, tweenId) { + if (tween) tween.kill(); - let insert = this.getInsertById(imgId); + let insert = this.getInsertById(imgId); if (insert) { // if the tweenId doesn't exist, do nothing more - if (!insert.tweens[tweenId]) - return; - if (!tween) - insert.tweens[tweenId].kill(); - insert.tweens[tweenId] = null; - let nTweens = {}; + if (!insert.tweens[tweenId]) return; + if (!tween) insert.tweens[tweenId].kill(); + insert.tweens[tweenId] = null; + let nTweens = {}; for (let prop in insert.tweens) { - if (insert.tweens[prop] != null) - nTweens[prop] = insert.tweens[prop]; + if (insert.tweens[prop] != null) nTweens[prop] = insert.tweens[prop]; } // replace after we removed the prop - insert.tweens = nTweens; + insert.tweens = nTweens; } - this.renderAnims--; + this.renderAnims--; //sanit check - if(this.renderAnims < 0) { - console.error("ERROR RENDER ANIM < 0 from %s of %s",tweenId,(insert ? insert.name : imgId)); - ui.notifications.error("ERROR RENDER ANIM < 0 "); + if (this.renderAnims < 0) { + console.error("ERROR RENDER ANIM < 0 from %s of %s", tweenId, insert ? insert.name : imgId); + ui.notifications.error("ERROR RENDER ANIM < 0 "); } } @@ -2220,36 +2156,31 @@ class Theatre { * @private */ _destroyPortraitDock(imgId) { - let app = this.pixiCTX; - let insert = this.getInsertById(imgId) + let app = this.pixiCTX; + let insert = this.getInsertById(imgId); if (insert && insert.dockContainer) { // kill and release all tweens - for (let tweenId in insert.tweens) - this._removeDockTween(imgId,null,tweenId); - insert.tweens = null; + for (let tweenId in insert.tweens) this._removeDockTween(imgId, null, tweenId); + insert.tweens = null; // destroy children - for (let child of insert.portraitContainer.children) - child.destroy(); - for (let child of insert.dockContainer.children) - child.destroy(); - insert.portrait = null; - insert.portraitContainer = null; - insert.label = null; + for (let child of insert.portraitContainer.children) child.destroy(); + for (let child of insert.dockContainer.children) child.destroy(); + insert.portrait = null; + insert.portraitContainer = null; + insert.label = null; // destroy self - insert.dockContainer.destroy(); - insert.dockContainer = null; - let idx = this.portraitDocks.findIndex(e => e.imgId == imgId); - this.portraitDocks.splice(idx,1); + insert.dockContainer.destroy(); + insert.dockContainer = null; + let idx = this.portraitDocks.findIndex((e) => e.imgId == imgId); + this.portraitDocks.splice(idx, 1); // The "MyTab" module inserts another element with id "pause". Use querySelectorAll to make sure we catch both - document.querySelectorAll("#pause").forEach(ele => KHelpers.removeClass(ele, "theatre-centered")); - $('#players').removeClass("theatre-invisible"); - $('#hotbar').removeClass("theatre-invisible"); + document.querySelectorAll("#pause").forEach((ele) => KHelpers.removeClass(ele, "theatre-centered")); + $("#players").removeClass("theatre-invisible"); + $("#hotbar").removeClass("theatre-invisible"); } // force a render update - //app.render(); - if (!this.rendering) - this._renderTheatre(performance.now()); - + //app.render(); + if (!this.rendering) this._renderTheatre(performance.now()); } /** @@ -2264,45 +2195,45 @@ class Theatre { * @params emotes (Object) : An Object containing properties pretaining to the emote state * to initialize the container with. * @params isLeft (Boolean) : Boolean to determine if this portrait should be injected - * left, or right in the dock after creation. + * left, or right in the dock after creation. * * @private */ - _createPortraitPIXIContainer(imgPath,portName,imgId,optAlign,emotions,isLeft) { + _createPortraitPIXIContainer(imgPath, portName, imgId, optAlign, emotions, isLeft) { // given an image, we will generate a PIXI container to add to the theatreDock and size // it to the image loaded - let dockContainer = new PIXI.Container(); - let portraitContainer = new PIXI.Container(); - dockContainer.addChild(portraitContainer); + let dockContainer = new PIXI.Container(); + let portraitContainer = new PIXI.Container(); + dockContainer.addChild(portraitContainer); // initial positioning portraitContainer.x = 0; portraitContainer.y = 0; - let app = this.pixiCTX; - app.stage.addChild(dockContainer); + let app = this.pixiCTX; + app.stage.addChild(dockContainer); // track the dockContainer if (!!this.getInsertById(imgId)) { // this dockContainer should be destroyed - console.log("PRE-EXISTING PIXI CONTAINER FOR %s ",imgId); - this._destroyPortraitDock(imgId); + console.log("PRE-EXISTING PIXI CONTAINER FOR %s ", imgId); + this._destroyPortraitDock(imgId); } - //console.log("Creating PortraintPIXIContainer with emotions: ",emotions); + //console.log("Creating PortraintPIXIContainer with emotions: ",emotions); - let ename,textFlyin,textStanding,textFont,textSize,textColor + let ename, textFlyin, textStanding, textFont, textSize, textColor; if (emotions) { - ename = emotions.emote; - textFlyin = emotions.textFlyin; - textStanding = emotions.textStanding; - textFont = emotions.textFont; - textSize = emotions.textSize; - textColor = emotions.textColor; + ename = emotions.emote; + textFlyin = emotions.textFlyin; + textStanding = emotions.textStanding; + textFont = emotions.textFont; + textSize = emotions.textSize; + textColor = emotions.textColor; } this.portraitDocks.push({ imgId: imgId, - dockContainer: dockContainer, + dockContainer: dockContainer, name: portName, emote: ename, textFlyin: textFlyin, @@ -2310,74 +2241,70 @@ class Theatre { textFont: textFont, textSize: textSize, textColor: textColor, - portraitContainer: portraitContainer, + portraitContainer: portraitContainer, portrait: null, - label: null, + label: null, typingBubble: null, - exitOrientation: (isLeft ? "left" : "right"), + exitOrientation: isLeft ? "left" : "right", nameOrientation: "left", mirrored: false, optAlign: optAlign, tweens: {}, order: 0, renderOrder: 0, - meta: {} - }); + meta: {}, + }); let imgSrcs = []; - imgSrcs.push({imgpath: "modules/theatre/app/graphics/typing.png", resname: "modules/theatre/app/graphics/typing.png"}); - imgSrcs.push({imgpath: imgPath, resname: imgPath}); - if (Theatre.DEBUG) console.log("Adding %s with src %s",portName,imgPath); + imgSrcs.push({ imgpath: "modules/theatre/app/graphics/typing.png", resname: "modules/theatre/app/graphics/typing.png" }); + imgSrcs.push({ imgpath: imgPath, resname: imgPath }); + if (Theatre.DEBUG) console.log("Adding %s with src %s", portName, imgPath); // get actor, load all emote images - let actorId = imgId.replace("theatre-",""); - let params = this._getInsertParamsFromActorId(actorId); + let actorId = imgId.replace("theatre-", ""); + let params = this._getInsertParamsFromActorId(actorId); if (!params) { - console.log("ERROR: Actor does not exist for %s",actorId); - this._destroyPortraitDock(imgId); - return null; + console.log("ERROR: Actor does not exist for %s", actorId); + this._destroyPortraitDock(imgId); + return null; } // load all rigging assets - let rigResources = Theatre.getActorRiggingResources(actorId); + let rigResources = Theatre.getActorRiggingResources(actorId); - if (Theatre.DEBUG) console.log("RigResources for %s :",portName,rigResources); - - for (let rigResource of rigResources) - imgSrcs.push({imgpath: rigResource.path, resname: rigResource.path}); + if (Theatre.DEBUG) console.log("RigResources for %s :", portName, rigResources); + + for (let rigResource of rigResources) imgSrcs.push({ imgpath: rigResource.path, resname: rigResource.path }); // load all emote base images + rigging for the emotes for (let emName in params.emotes) if (params.emotes[emName]) - if (params.emotes[emName].insert && params.emotes[emName].insert != "") - imgSrcs.push({imgpath: params.emotes[emName].insert, resname: params.emotes[emName].insert}); + if (params.emotes[emName].insert && params.emotes[emName].insert != "") + imgSrcs.push({ imgpath: params.emotes[emName].insert, resname: params.emotes[emName].insert }); // handles the waiting game of grabbing loader for us - this._addSpritesToPixi(imgSrcs, (loader, resources)=>{ + this._addSpritesToPixi(imgSrcs, (loader, resources) => { // PIXI Container is ready! // Setup the dockContainer to display the base insert - if (Theatre.DEBUG) console.log("Sprites added to PIXI _createPortraitPIXIContainer",resources); - let portWidth = (ename && params.emotes[ename] && params.emotes[ename].insert) ? - resources[params.emotes[ename].insert].texture.width : resources[imgPath].texture.width; - let initX = isLeft ? (-1 * portWidth) : (this.theatreDock.offsetWidth + portWidth); + if (Theatre.DEBUG) console.log("Sprites added to PIXI _createPortraitPIXIContainer", resources); + let portWidth = ename && params.emotes[ename] && params.emotes[ename].insert ? resources[params.emotes[ename].insert].texture.width : resources[imgPath].texture.width; + let initX = isLeft ? -1 * portWidth : this.theatreDock.offsetWidth + portWidth; if (!ename) { // load in default portrait - dockContainer.x = initX; - this._setupPortraitContainer(imgId,optAlign,imgPath,resources,true); + dockContainer.x = initX; + this._setupPortraitContainer(imgId, optAlign, imgPath, resources, true); } else { // load in the ename emote portrait instead if possible, else load the default if (params.emotes[ename] && params.emotes[ename].insert) { - dockContainer.x = isLeft ? - (-1 * portWidth) : (this.theatreDock.offsetWidth + portWidth); - this._setupPortraitContainer(imgId,optAlign,params.emotes[ename].insert,resources,true); + dockContainer.x = isLeft ? -1 * portWidth : this.theatreDock.offsetWidth + portWidth; + this._setupPortraitContainer(imgId, optAlign, params.emotes[ename].insert, resources, true); } else { - dockContainer.x = initX; - this._setupPortraitContainer(imgId,optAlign,imgPath,resources,true); + dockContainer.x = initX; + this._setupPortraitContainer(imgId, optAlign, imgPath, resources, true); } } - - }); + }); } /** @@ -2388,35 +2315,39 @@ class Theatre { * @params resName (String) : The resource name of the sprite to configure. * @params resources (Object) : The resource object from PIXI.Loader.shared. * @params reorder (Boolean) : Boolean to indicate if a reorder should be performed after - * an update. + * an update. * * @private */ - _setupPortraitContainer(imgId,optAlign,resName,resources,reorder) { - let insert = this.getInsertById(imgId); + _setupPortraitContainer(imgId, optAlign, resName, resources, reorder) { + let insert = this.getInsertById(imgId); - if (!insert || !insert.dockContainer) { - console.error("ERROR PIXI Container was destroyed before setup could execute for %s",imgId); - ui.notifications.error(`${game.i18n.localize("Theatre.UI.Notification.ImageLoadFail_P1")} ${imgId} ${game.i18n.localize("Theatre.UI.Notification.ImageLoadFail_P2")} ${resName}`); - this.removeInsertById(imgId); - return; + if (!insert || !insert.dockContainer) { + console.error("ERROR PIXI Container was destroyed before setup could execute for %s", imgId); + ui.notifications.error( + `${game.i18n.localize("Theatre.UI.Notification.ImageLoadFail_P1")} ${imgId} ${game.i18n.localize("Theatre.UI.Notification.ImageLoadFail_P2")} ${resName}` + ); + this.removeInsertById(imgId); + return; } if (!resources[resName] || !resources[resName].texture) { - console.error("ERROR could not load texture %s",resName,resources); - ui.notifications.error(`${game.i18n.localize("Theatre.UI.Notification.ImageLoadFail_P1")} ${imgId} ${game.i18n.localize("Theatre.UI.Notification.ImageLoadFail_P2")} ${resName}`); - this.removeInsertById(imgId); - return; + console.error("ERROR could not load texture %s", resName, resources); + ui.notifications.error( + `${game.i18n.localize("Theatre.UI.Notification.ImageLoadFail_P1")} ${imgId} ${game.i18n.localize("Theatre.UI.Notification.ImageLoadFail_P2")} ${resName}` + ); + this.removeInsertById(imgId); + return; } - let app = this.pixiCTX; - let dockContainer = insert.dockContainer; - let portraitContainer = insert.portraitContainer; + let app = this.pixiCTX; + let dockContainer = insert.dockContainer; + let portraitContainer = insert.portraitContainer; let sprite = new PIXI.Sprite(resources[resName].texture); - let portWidth = resources[resName].texture.width; - let portHeight = resources[resName].texture.height; - let maxHeight = game.settings.get(Theatre.SETTINGS,"theatreImageSize"); + let portWidth = resources[resName].texture.width; + let portHeight = resources[resName].texture.height; + let maxHeight = game.settings.get(Theatre.SETTINGS, "theatreImageSize"); if (portHeight > maxHeight) { portWidth *= maxHeight / portHeight; portHeight = maxHeight; @@ -2424,30 +2355,30 @@ class Theatre { // adjust dockContainer + portraitContainer dimensions to fit the image dockContainer.width = portWidth; - dockContainer.height = portHeight; + dockContainer.height = portHeight; portraitContainer.width = portWidth; - portraitContainer.height = portHeight; + portraitContainer.height = portHeight; // set the initial dockContainer position + state //dockContainer.x = 0; - dockContainer.y = this.theatreDock.offsetHeight - (optAlign == "top" ? this.theatreBar.offsetHeight : 0) - portHeight; - + dockContainer.y = this.theatreDock.offsetHeight - (optAlign == "top" ? this.theatreBar.offsetHeight : 0) - portHeight; + // save and stage our sprite insert.portrait = sprite; insert.portrait.width = portWidth; insert.portrait.height = portHeight; portraitContainer.addChild(sprite); - portraitContainer.pivot.x = portWidth/2; - portraitContainer.pivot.y = portHeight/2; - portraitContainer.x = portraitContainer.x + portWidth/2; - portraitContainer.y = portraitContainer.y + portHeight/2; + portraitContainer.pivot.x = portWidth / 2; + portraitContainer.pivot.y = portHeight / 2; + portraitContainer.x = portraitContainer.x + portWidth / 2; + portraitContainer.y = portraitContainer.y + portHeight / 2; // set sprite initial coordinates + state - sprite.x = 0; - sprite.y = 0; + sprite.x = 0; + sprite.y = 0; // set mirror state if mirrored if (insert.mirrored) { - portraitContainer.scale.x = -1; + portraitContainer.scale.x = -1; /* if (reorder) portraitContainer.x = portWidth; @@ -2457,188 +2388,185 @@ class Theatre { if (!insert.label) { let textStyle = new PIXI.TextStyle({ align: "center", - fontFamily: game.settings.get(Theatre.SETTINGS,"nameFont"), + fontFamily: game.settings.get(Theatre.SETTINGS, "nameFont"), fontSize: 44, lineHeight: 64, //fontStyle: 'italic', fontWeight: this.fontWeight, - fill: ['#ffffff'], - stroke: '#000000', + fill: ["#ffffff"], + stroke: "#000000", strokeThickness: 2, dropShadow: true, - dropShadowColor: '#000000', + dropShadowColor: "#000000", dropShadowBlur: 1, dropShadowAngle: Math.PI / 6, breakWords: true, wordWrap: true, - wordWrapWidth: portWidth - }); - let label = new PIXI.Text(insert.name,textStyle); + wordWrapWidth: portWidth, + }); + let label = new PIXI.Text(insert.name, textStyle); // save and stage our label - label.theatreComponentName = "label"; - insert.label = label; - dockContainer.addChild(label); + label.theatreComponentName = "label"; + insert.label = label; + dockContainer.addChild(label); // initital positioning insert.label.x = 20; } // position the label - insert.label.y = portHeight - (optAlign == "top" ? 0 : this.theatreBar.offsetHeight) - insert.label.lineHeight - 20; + insert.label.y = portHeight - (optAlign == "top" ? 0 : this.theatreBar.offsetHeight) - insert.label.lineHeight - 20; // setup typing bubble if (!insert.typingBubble) { - let typingBubble = new PIXI.Sprite(); - typingBubble.texture = resources["modules/theatre/app/graphics/typing.png"].texture; - typingBubble.width = 55; - typingBubble.height = 55; - typingBubble.theatreComponentName = "typingBubble"; - typingBubble.alpha = 0; - typingBubble.y = portHeight - - (optAlign == "top" ? 0 : this.theatreBar.offsetHeight) - insert.label.style.lineHeight + typingBubble.height/2; + let typingBubble = new PIXI.Sprite(); + typingBubble.texture = resources["modules/theatre/app/graphics/typing.png"].texture; + typingBubble.width = 55; + typingBubble.height = 55; + typingBubble.theatreComponentName = "typingBubble"; + typingBubble.alpha = 0; + typingBubble.y = portHeight - (optAlign == "top" ? 0 : this.theatreBar.offsetHeight) - insert.label.style.lineHeight + typingBubble.height / 2; - insert.typingBubble = typingBubble; - dockContainer.addChild(typingBubble); + insert.typingBubble = typingBubble; + dockContainer.addChild(typingBubble); } // TheatreStyle specific adjustments switch (this.settings.theatreStyle) { case "lightbox": // to allow top-aligned portraits to work without a seam - dockContainer.y += (optAlign == "top" ? 8 : 0); - insert.label.y -= (insert.optAlign == "top" ? 8 : 0); - break; + dockContainer.y += optAlign == "top" ? 8 : 0; + insert.label.y -= insert.optAlign == "top" ? 8 : 0; + break; case "clearbox": - dockContainer.y = this.theatreDock.offsetHeight - portHeight; - insert.label.y += (optAlign == "top" ? 0 : this.theatreBar.offsetHeight); - insert.typingBubble.y += (optAlign == "top" ? 0 : this.theatreBar.offsetHeight); - break; + dockContainer.y = this.theatreDock.offsetHeight - portHeight; + insert.label.y += optAlign == "top" ? 0 : this.theatreBar.offsetHeight; + insert.typingBubble.y += optAlign == "top" ? 0 : this.theatreBar.offsetHeight; + break; case "mangabubble": - break; + break; case "textbox": - break; + break; default: - break; + break; } - - if (Theatre.DEBUG) console.log("Portrait loaded with w:%s h:%s",portWidth,portHeight,sprite); + + if (Theatre.DEBUG) console.log("Portrait loaded with w:%s h:%s", portWidth, portHeight, sprite); // run rigging animations if we have have any if (insert.emote) { - let actorId = insert.imgId.replace("theatre-",""); - let defaultDisabled = this.isDefaultDisabled(insert.imgId); - if (Theatre.DEBUG) console.log("is default disabled? : %s",defaultDisabled); - let emotes = Theatre.getActorEmotes(actorId,defaultDisabled); - let rigResMap = Theatre.getActorRiggingResources(actorId); + let actorId = insert.imgId.replace("theatre-", ""); + let defaultDisabled = this.isDefaultDisabled(insert.imgId); + if (Theatre.DEBUG) console.log("is default disabled? : %s", defaultDisabled); + let emotes = Theatre.getActorEmotes(actorId, defaultDisabled); + let rigResMap = Theatre.getActorRiggingResources(actorId); if (emotes[insert.emote] && emotes[insert.emote].rigging) { for (let anim of emotes[insert.emote].rigging.animations) { - this.addTweensFromAnimationSyntax(anim.name,anim.syntax,rigResMap,insert); + this.addTweensFromAnimationSyntax(anim.name, anim.syntax, rigResMap, insert); } } } if (Theatre.DEBUG) { // DEBUG BOX dockContainer - let graphics = new PIXI.Graphics(); - graphics.lineStyle (1,0xFEEB77,1); - graphics.moveTo(0,0); - graphics.lineTo(portWidth,0); - graphics.lineTo(portWidth,portHeight); - graphics.lineTo(0,portHeight); - graphics.lineTo(0,0); - dockContainer.addChild(graphics); + let graphics = new PIXI.Graphics(); + graphics.lineStyle(1, 0xfeeb77, 1); + graphics.moveTo(0, 0); + graphics.lineTo(portWidth, 0); + graphics.lineTo(portWidth, portHeight); + graphics.lineTo(0, portHeight); + graphics.lineTo(0, 0); + dockContainer.addChild(graphics); let dimStyle = new PIXI.TextStyle({ fontSize: 10, lineHeight: 30, fontWeight: "bold", - fill: ['#FF383A'], - stroke: '#000000', + fill: ["#FF383A"], + stroke: "#000000", strokeThickness: 2, wordWrap: true, - wordWrapWidth: portWidth - }); + wordWrapWidth: portWidth, + }); let pathStyle = new PIXI.TextStyle({ fontSize: 22, lineHeight: 22, fontWeight: "bold", - fill: ['#38FFEB'], - stroke: '#000000', + fill: ["#38FFEB"], + stroke: "#000000", strokeThickness: 2, wordWrap: true, breakWords: true, - wordWrapWidth: portWidth - }); + wordWrapWidth: portWidth, + }); let infoStyle = new PIXI.TextStyle({ fontSize: 14, lineHeight: 14, fontWeight: "bold", - fill: ['#ffffff'], - stroke: '#000000', + fill: ["#ffffff"], + stroke: "#000000", strokeThickness: 2, wordWrap: true, breakWords: true, - wordWrapWidth: portWidth - }); - let dims = new PIXI.Text(`${portWidth} px x ${portHeight} px`,dimStyle); - let path = new PIXI.Text(resources[resName].url,pathStyle); - let info = new PIXI.Text("X",infoStyle); - info.theatreComponentName = "debugInfo"; - dims.x = 20; - path.x = 20; - path.y = 30; - info.x = 20; - info.y = 90; - dockContainer.addChild(dims); - dockContainer.addChild(path); - dockContainer.addChild(info); - this._updateTheatreDebugInfo(insert); + wordWrapWidth: portWidth, + }); + let dims = new PIXI.Text(`${portWidth} px x ${portHeight} px`, dimStyle); + let path = new PIXI.Text(resources[resName].url, pathStyle); + let info = new PIXI.Text("X", infoStyle); + info.theatreComponentName = "debugInfo"; + dims.x = 20; + path.x = 20; + path.y = 30; + info.x = 20; + info.y = 90; + dockContainer.addChild(dims); + dockContainer.addChild(path); + dockContainer.addChild(info); + this._updateTheatreDebugInfo(insert); // DEBUG BOX portraitContainer - graphics = new PIXI.Graphics(); - graphics.lineStyle (1,0xFFFFFF,1); - graphics.moveTo(0,0); - graphics.lineTo(portWidth,0); - graphics.lineTo(portWidth,portHeight); - graphics.lineTo(0,portHeight); - graphics.lineTo(0,0); - portraitContainer.addChild(graphics); + graphics = new PIXI.Graphics(); + graphics.lineStyle(1, 0xffffff, 1); + graphics.moveTo(0, 0); + graphics.lineTo(portWidth, 0); + graphics.lineTo(portWidth, portHeight); + graphics.lineTo(0, portHeight); + graphics.lineTo(0, 0); + portraitContainer.addChild(graphics); } if (reorder) { // fade in - dockContainer.alpha = 0; + dockContainer.alpha = 0; - window.setTimeout(()=>{ + window.setTimeout(() => { let tb = this._getTextBoxById(imgId); - if (tb) tb.style.opacity = 1; - - window.clearTimeout(this.reorderTOId) - this.reorderTOId = window.setTimeout(()=>{ - Theatre.reorderInserts(); - this.reorderTOId = null; - },500); - },100); + if (tb) tb.style.opacity = 1; + + window.clearTimeout(this.reorderTOId); + this.reorderTOId = window.setTimeout(() => { + Theatre.reorderInserts(); + this.reorderTOId = null; + }, 500); + }, 100); } else { - dockContainer.alpha = 1; + dockContainer.alpha = 1; } - //app.render(); - if (!this.rendering) - this._renderTheatre(performance.now()); + //app.render(); + if (!this.rendering) this._renderTheatre(performance.now()); } /** * - * Updates the PIXIText containing our debug information. + * Updates the PIXIText containing our debug information. * * @params insert (Objet) : An Object represeting the insert * * @private */ _updateTheatreDebugInfo(insert) { - if (!insert || !insert.dockContainer) - return; - let info = insert.dockContainer.children.find(e => e.theatreComponentName == "debugInfo"); + if (!insert || !insert.dockContainer) return; + let info = insert.dockContainer.children.find((e) => e.theatreComponentName == "debugInfo"); if (info) { - info.text = ( + info.text = `imgId: ${insert.imgId}\n` + `dockContainer (exists): ${!!insert.dockContainer}\n` + `name: ${insert.name}\n` + @@ -2661,11 +2589,10 @@ class Theatre { `tweens (# active): ${Object.keys(insert.tweens).length}\n` + `decayTOId: ${insert.decayTOId}\n` + `order: ${insert.order}\n` + - `renderOrder: ${insert.renderOrder}\n` - /* + `renderOrder: ${insert.renderOrder}\n`; + /* `meta (#): ${insert.meta.length}\n` */ - ); } } @@ -2680,85 +2607,79 @@ class Theatre { */ _repositionInsertElements(insert) { if (!insert || !insert.portrait) { - console.log("ERROR: No insert, or portrait available ", insert); - return; + console.log("ERROR: No insert, or portrait available ", insert); + return; } // re-align the dockContainer to the textBox and its nameOrientation - let textBox = this.getTextBoxById(insert.imgId); - let offset = KHelpers.offset(textBox); + let textBox = this.getTextBoxById(insert.imgId); + let offset = KHelpers.offset(textBox); let leftPos = Math.round( - Number(offset.left || 0) - - Number(KHelpers.style(textBox)["left"].match(/\-*\d+\.*\d*/) || 0) - - Number(KHelpers.style(this.theatreBar)["margin-left"].match(/\-*\d+\.*\d*/) || 0) - ); + Number(offset.left || 0) - + Number(KHelpers.style(textBox)["left"].match(/\-*\d+\.*\d*/) || 0) - + Number(KHelpers.style(this.theatreBar)["margin-left"].match(/\-*\d+\.*\d*/) || 0) + ); // pre-split measurement - insert.label.style.wordWrap = false; - insert.label.style.wordWrapWidth = insert.portrait.width; - let labelExceeds = (insert.label.width+20+insert.label.style.fontSize) > textBox.offsetWidth; - let preLabelWidth = insert.label.width; + insert.label.style.wordWrap = false; + insert.label.style.wordWrapWidth = insert.portrait.width; + let labelExceeds = insert.label.width + 20 + insert.label.style.fontSize > textBox.offsetWidth; + let preLabelWidth = insert.label.width; // split measurement - insert.label.style.wordWrap = true; - insert.label.style.wordWrapWidth = textBox.offsetWidth; + insert.label.style.wordWrap = true; + insert.label.style.wordWrapWidth = textBox.offsetWidth; // Scale the name bar length and orient the portait if (insert.nameOrientation == "left") { - insert.label.x = 20; - insert.typingBubble.anchor.set(0.5); - insert.typingBubble.x = Math.min(preLabelWidth + 20 + insert.typingBubble.width/2, textBox.offsetWidth - insert.typingBubble.width/2); - + insert.label.x = 20; + insert.typingBubble.anchor.set(0.5); + insert.typingBubble.x = Math.min(preLabelWidth + 20 + insert.typingBubble.width / 2, textBox.offsetWidth - insert.typingBubble.width / 2); } else { if (labelExceeds) { - insert.label.x = insert.portrait.width - insert.label.width - 20; + insert.label.x = insert.portrait.width - insert.label.width - 20; if (insert.label.width - 20 > insert.portrait.width) - insert.typingBubble.x = Math.min(insert.portrait.width - insert.label.width - insert.typingBubble.texture.width/2 - 20, insert.typingBubble.width/2); - else - insert.typingBubble.x = Math.max(insert.portrait.width - insert.label.width - insert.typingBubble.texture.width/2 - 20, insert.typingBubble.width/2); + insert.typingBubble.x = Math.min(insert.portrait.width - insert.label.width - insert.typingBubble.texture.width / 2 - 20, insert.typingBubble.width / 2); + else insert.typingBubble.x = Math.max(insert.portrait.width - insert.label.width - insert.typingBubble.texture.width / 2 - 20, insert.typingBubble.width / 2); } else { - insert.label.x = insert.portrait.width - preLabelWidth - 20; + insert.label.x = insert.portrait.width - preLabelWidth - 20; if (preLabelWidth - 20 > insert.portrait.width) - insert.typingBubble.x = Math.min(insert.portrait.width - preLabelWidth - insert.typingBubble.texture.width/2 - 20, insert.typingBubble.width/2); - else - insert.typingBubble.x = Math.max(insert.portrait.width - preLabelWidth - insert.typingBubble.texture.width/2 - 20, insert.typingBubble.width/2); + insert.typingBubble.x = Math.min(insert.portrait.width - preLabelWidth - insert.typingBubble.texture.width / 2 - 20, insert.typingBubble.width / 2); + else insert.typingBubble.x = Math.max(insert.portrait.width - preLabelWidth - insert.typingBubble.texture.width / 2 - 20, insert.typingBubble.width / 2); } - insert.typingBubble.anchor.set(0.5); + insert.typingBubble.anchor.set(0.5); - leftPos += textBox.offsetWidth - insert.portrait.width; + leftPos += textBox.offsetWidth - insert.portrait.width; } - insert.typingBubble.y = insert.portrait.height - - (insert.optAlign == "top" ? 0 : Theatre.instance.theatreBar.offsetHeight) - insert.label.style.lineHeight + insert.typingBubble.height/2; + insert.typingBubble.y = + insert.portrait.height - (insert.optAlign == "top" ? 0 : Theatre.instance.theatreBar.offsetHeight) - insert.label.style.lineHeight + insert.typingBubble.height / 2; // if the label height > font-size, it word wrapped wrap, so we need to bump up the height if (labelExceeds) { - let divisor = Math.round(insert.label.height/insert.label.style.lineHeight); - insert.label.y = insert.portrait.height - - (insert.optAlign == "top" ? 0 : Theatre.instance.theatreBar.offsetHeight) - (insert.label.style.lineHeight*divisor); + let divisor = Math.round(insert.label.height / insert.label.style.lineHeight); + insert.label.y = insert.portrait.height - (insert.optAlign == "top" ? 0 : Theatre.instance.theatreBar.offsetHeight) - insert.label.style.lineHeight * divisor; } else { // normal - insert.label.y = insert.portrait.height - - (insert.optAlign == "top" ? 0 : Theatre.instance.theatreBar.offsetHeight) - insert.label.style.lineHeight; + insert.label.y = insert.portrait.height - (insert.optAlign == "top" ? 0 : Theatre.instance.theatreBar.offsetHeight) - insert.label.style.lineHeight; } - insert.typingBubble.rotation = 0.1745; - insert.dockContainer.x = leftPos; - insert.dockContainer.y = this.theatreDock.offsetHeight - - (insert.optAlign == "top" ? this.theatreBar.offsetHeight : 0) - insert.portrait.height; + insert.typingBubble.rotation = 0.1745; + insert.dockContainer.x = leftPos; + insert.dockContainer.y = this.theatreDock.offsetHeight - (insert.optAlign == "top" ? this.theatreBar.offsetHeight : 0) - insert.portrait.height; // theatreStyle specific adjustments switch (this.settings.theatreStyle) { case "lightbox": // to allow top-aligned portraits to work without a seam - insert.dockContainer.y += (insert.optAlign == "top" ? 8 : 0); - insert.label.y -= (insert.optAlign == "top" ? 8 : 0); - break; + insert.dockContainer.y += insert.optAlign == "top" ? 8 : 0; + insert.label.y -= insert.optAlign == "top" ? 8 : 0; + break; case "clearbox": - insert.dockContainer.y = this.theatreDock.offsetHeight - insert.portrait.height; - insert.label.y += (insert.optAlign == "top" ? 0 : Theatre.instance.theatreBar.offsetHeight); - insert.typingBubble.y += (insert.optAlign == "top" ? 0 : Theatre.instance.offsetHeight); - break; + insert.dockContainer.y = this.theatreDock.offsetHeight - insert.portrait.height; + insert.label.y += insert.optAlign == "top" ? 0 : Theatre.instance.theatreBar.offsetHeight; + insert.typingBubble.y += insert.optAlign == "top" ? 0 : Theatre.instance.offsetHeight; + break; case "mangabubble": - break; + break; case "textbox": - break; + break; default: - break; + break; } } @@ -2775,7 +2696,7 @@ class Theatre { * * @private */ - async _AddTextureResource(imgSrc,resName,imgId,emote,cb,remote) { + async _AddTextureResource(imgSrc, resName, imgId, emote, cb, remote) { // First we pull the insert,canvas,and pixi app from the imgId. // Second, we want to verify that the source image exists, if so, // then we'll proceed. @@ -2786,18 +2707,18 @@ class Theatre { // also replace their resources. // ** NOTE this may have desync issues ** - let insert = this.getInsertById(imgId); - let container = (insert ? insert.dockContainer : null); + let insert = this.getInsertById(imgId); + let container = insert ? insert.dockContainer : null; // If no insert/container, this is fine - let app = this.pixiCTX; - let actorId = imgId.replace("theatre-",""); - let actorParams = this._getInsertParamsFromActorId(actorId); + let app = this.pixiCTX; + let actorId = imgId.replace("theatre-", ""); + let actorParams = this._getInsertParamsFromActorId(actorId); // no actor is also fine if this is some kind of rigging resource // src check, not fine at all! - if (!await srcExists(imgSrc)) { - console.log("ERROR (_AddTextureResource) : Replacement texture does not exist %s ",imgSrc); - return; + if (!(await srcExists(imgSrc))) { + console.log("ERROR (_AddTextureResource) : Replacement texture does not exist %s ", imgSrc); + return; } let loader = PIXI.Loader.shared; @@ -2808,31 +2729,30 @@ class Theatre { // if we have no resName then just return the cb if (!resName || resName == "") { - cb.call(this,loader,loader.resources); - return; + cb.call(this, loader, loader.resources); + return; } - let imgSrcs = [{resname: resName, imgpath: imgSrc}]; - if (Theatre.DEBUG) console.log("replace textures",imgSrcs); - this._addSpritesToPixi(imgSrcs, (loader, resources)=>{ - cb.call(this,loader,resources); - }); + let imgSrcs = [{ resname: resName, imgpath: imgSrc }]; + if (Theatre.DEBUG) console.log("replace textures", imgSrcs); + this._addSpritesToPixi(imgSrcs, (loader, resources) => { + cb.call(this, loader, resources); + }); // Send to socket if (!remote) { // broadcast change to clients - this._sendSceneEvent("addtexture",{ + this._sendSceneEvent("addtexture", { insertid: imgId, imgsrc: imgSrc, resname: resName, - emote: emote - }); + emote: emote, + }); } - } /** - * Add All Texture Resources + * Add All Texture Resources * * Add an array of assets to the PIXI Loader * @@ -2842,11 +2762,11 @@ class Theatre { * @param emote (String) : The currently active emote, if any. * @param cb (Function) : The function callback to invoke when the resources are loaded. * @param remote (Boolean) : Wither or not this function is being invoked remotely, if not, then - * we want to broadcast to all other clients to perform the action as well. + * we want to broadcast to all other clients to perform the action as well. * * @private */ - async _AddAllTextureResources(imgSrcs,imgId,emote,eresName,cb,remote) { + async _AddAllTextureResources(imgSrcs, imgId, emote, eresName, cb, remote) { // First we pull the insert,canvas,and pixi app from the imgId. // Second, we want to verify that the source image exists, if so, // then we'll proceed. @@ -2857,19 +2777,19 @@ class Theatre { // also replace their resources. // ** NOTE this may have desync issues ** - let insert = this.getInsertById(imgId); - let container = (insert ? insert.dockContainer : null); + let insert = this.getInsertById(imgId); + let container = insert ? insert.dockContainer : null; // If no insert/container, this is fine - let app = this.pixiCTX; - let actorId = imgId.replace("theatre-",""); - let actorParams = this._getInsertParamsFromActorId(actorId); + let app = this.pixiCTX; + let actorId = imgId.replace("theatre-", ""); + let actorParams = this._getInsertParamsFromActorId(actorId); // no actor is also fine if this is some kind of rigging resource // src check, not fine at all! for (let src of imgSrcs) - if (!await srcExists(src.imgpath)) { - console.log("ERROR (_AddAllTextureResources) : Replacement texture does not exist %s ",src); - return; + if (!(await srcExists(src.imgpath))) { + console.log("ERROR (_AddAllTextureResources) : Replacement texture does not exist %s ", src); + return; } let loader = PIXI.Loader.shared; @@ -2880,109 +2800,92 @@ class Theatre { // if we have an emtpy imgSrc array, just return the cb if (imgSrcs.length <= 0) { - cb.call(this,loader,loader.resources); - return; + cb.call(this, loader, loader.resources); + return; } - if (Theatre.DEBUG) console.log("replace textures",imgSrcs); - this._addSpritesToPixi(imgSrcs, (loader, resources)=>{ - cb.call(this,loader,resources); - }); + if (Theatre.DEBUG) console.log("replace textures", imgSrcs); + this._addSpritesToPixi(imgSrcs, (loader, resources) => { + cb.call(this, loader, resources); + }); // Send to socket if (!remote) { // broadcast change to clients - this._sendSceneEvent("addalltextures",{ + this._sendSceneEvent("addalltextures", { insertid: imgId, imgsrcs: imgSrcs, emote: emote, - eresname: eresName - }); + eresname: eresName, + }); } - } - /** * Clear the container by ending all animations, and removing all sprites * * @param imgId : The theatreId of the insert whose dockContainer we should - * clear. + * clear. * * @private */ _clearPortraitContainer(imgId) { - let insert = this.getInsertById(imgId); - if (!insert || !insert.dockContainer || !insert.portrait) return; + let insert = this.getInsertById(imgId); + if (!insert || !insert.dockContainer || !insert.portrait) return; // preserve position without portrait offset - let ox = insert.portraitContainer.x - insert.portrait.width/2; - let oy = insert.portraitContainer.y - insert.portrait.height/2; - let ocx = insert.dockContainer.x; - let ocy = insert.dockContainer.y; - let oLabelAnim = insert.tweens["nameSpeakingPulse"]; - let oTypingBounceAnim = insert.tweens["typingBounce"]; - let oTypingWiggleAnim = insert.tweens["typingWiggle"]; - let oTypingAppearAnim = insert.tweens["typingAppear"]; - let oTypingVanishAnim = insert.tweens["typingVanish"]; + let ox = insert.portraitContainer.x - insert.portrait.width / 2; + let oy = insert.portraitContainer.y - insert.portrait.height / 2; + let ocx = insert.dockContainer.x; + let ocy = insert.dockContainer.y; + let oLabelAnim = insert.tweens["nameSpeakingPulse"]; + let oTypingBounceAnim = insert.tweens["typingBounce"]; + let oTypingWiggleAnim = insert.tweens["typingWiggle"]; + let oTypingAppearAnim = insert.tweens["typingAppear"]; + let oTypingVanishAnim = insert.tweens["typingVanish"]; // kill and release all tweens, except for label or typingBubble // animation for (let tweenId in insert.tweens) { - if (tweenId == "nameSpeakingPulse" - || tweenId == "typingBounce" - || tweenId == "typingAppear" - || tweenId == "typingVanish" - || tweenId == "typingWiggle") - continue; - this._removeDockTween(imgId,null,tweenId); - } - insert.tweens = {}; - if (oLabelAnim) - insert.tweens["nameSpeakingPulse"] = oLabelAnim; - if (oTypingBounceAnim) - insert.tweens["typingBounce"] = oTypingBounceAnim; - if (oTypingWiggleAnim) - insert.tweens["typingWiggle"] = oTypingWiggleAnim; - if (oTypingAppearAnim) - insert.tweens["typingAppear"] = oTypingAppearAnim; - if (oTypingVanishAnim) - insert.tweens["typingVanish"] = oTypingVanishAnim; + if (tweenId == "nameSpeakingPulse" || tweenId == "typingBounce" || tweenId == "typingAppear" || tweenId == "typingVanish" || tweenId == "typingWiggle") continue; + this._removeDockTween(imgId, null, tweenId); + } + insert.tweens = {}; + if (oLabelAnim) insert.tweens["nameSpeakingPulse"] = oLabelAnim; + if (oTypingBounceAnim) insert.tweens["typingBounce"] = oTypingBounceAnim; + if (oTypingWiggleAnim) insert.tweens["typingWiggle"] = oTypingWiggleAnim; + if (oTypingAppearAnim) insert.tweens["typingAppear"] = oTypingAppearAnim; + if (oTypingVanishAnim) insert.tweens["typingVanish"] = oTypingVanishAnim; // destroy children - for (let child of insert.portraitContainer.children) - child.destroy(); + for (let child of insert.portraitContainer.children) child.destroy(); // attempt to preserve label + typingBubble - for (let idx=insert.dockContainer.children.length-1; idx >=0; --idx) { - let child = insert.dockContainer.children[idx]; - if (child.theatreComponentName && child.theatreComponentName == "label") - insert.dockContainer.removeChildAt(idx); - else if (child.theatreComponentName && child.theatreComponentName == "typingBubble") - insert.dockContainer.removeChildAt(idx); - else - child.destroy(); - } - insert.portrait = null; - insert.portraitContainer = null; + for (let idx = insert.dockContainer.children.length - 1; idx >= 0; --idx) { + let child = insert.dockContainer.children[idx]; + if (child.theatreComponentName && child.theatreComponentName == "label") insert.dockContainer.removeChildAt(idx); + else if (child.theatreComponentName && child.theatreComponentName == "typingBubble") insert.dockContainer.removeChildAt(idx); + else child.destroy(); + } + insert.portrait = null; + insert.portraitContainer = null; // destroy self - insert.dockContainer.destroy(); - insert.dockContainer = null; + insert.dockContainer.destroy(); + insert.dockContainer = null; // re-generate the container - let dockContainer = new PIXI.Container(); - let portraitContainer = new PIXI.Container(); - dockContainer.addChild(portraitContainer); + let dockContainer = new PIXI.Container(); + let portraitContainer = new PIXI.Container(); + dockContainer.addChild(portraitContainer); // initial positioning portraitContainer.x = ox; portraitContainer.y = oy; dockContainer.x = ocx; - dockContainer.y = ocy + dockContainer.y = ocy; // assignment - insert.dockContainer = dockContainer; - insert.portraitContainer = portraitContainer; - if (Theatre.DEBUG) console.log("saving ox: %s, oy: %s",ox,oy); + insert.dockContainer = dockContainer; + insert.portraitContainer = portraitContainer; + if (Theatre.DEBUG) console.log("saving ox: %s, oy: %s", ox, oy); // label is NOT re-attached, must be done by the clearer // typingBubble is NOT re-attached, must be done by the clearer // mirror-state is NOT restored, must be done by the clearer - } /** @@ -2990,35 +2893,33 @@ class Theatre { * * @params imcSrcs (Array[Object]) : An array of {imgsrc: (String), resname (String)} pairs * representing the assets to be loaded into PIXI's loader. - * @params cb (Function) : The function to invoke once the assets are loaded. + * @params cb (Function) : The function to invoke once the assets are loaded. * * @private */ _addSpritesToPixi(imgSrcs, cb) { - if (Theatre.DEBUG) console.log("adding sprite to dockContainer"); - let loader = PIXI.Loader.shared; + if (Theatre.DEBUG) console.log("adding sprite to dockContainer"); + let loader = PIXI.Loader.shared; // Load in our resources if needed - // if loader is running, we will stick a timeout and wait, // possibly fighting with others on the event looop for the loader if (!loader.loading) { - if (Theatre.DEBUG) console.log("resources",loader); + if (Theatre.DEBUG) console.log("resources", loader); for (let imgTuple of imgSrcs) { - let resName = imgTuple.resname; - if (!loader.resources[resName]) - loader.add(resName,imgTuple.imgpath); + let resName = imgTuple.resname; + if (!loader.resources[resName]) loader.add(resName, imgTuple.imgpath); } - loader.load((loader,resources)=>{ - cb.call(this,loader,resources); - }); + loader.load((loader, resources) => { + cb.call(this, loader, resources); + }); } else { - window.setTimeout(()=>{ - if (Theatre.DEBUG) console.log("loader not done, waiting"); - this._getLoaderChainWait(this,imgSrcs,cb).call(this); - },200); + window.setTimeout(() => { + if (Theatre.DEBUG) console.log("loader not done, waiting"); + this._getLoaderChainWait(this, imgSrcs, cb).call(this); + }, 200); } } @@ -3028,152 +2929,148 @@ class Theatre { * @params ctx (Context) : The context to invoke the callback with * @params imcSrcs (Array[Object]) : An array of {imgsrc: (String), resname (String)} pairs * representing the assets to be loaded into PIXI's loader. - * @params cb (Function) : The function to invoke once the assets are loaded. + * @params cb (Function) : The function to invoke once the assets are loaded. * * @private */ - _getLoaderChainWait(ctx,imgSrcs,cb) { - let loader = PIXI.Loader.shared; + _getLoaderChainWait(ctx, imgSrcs, cb) { + let loader = PIXI.Loader.shared; let func = function () { if (!loader.loading) { - if (Theatre.DEBUG) console.log("delayed loading resources",loader); + if (Theatre.DEBUG) console.log("delayed loading resources", loader); for (let imgTuple of imgSrcs) { - let resName = imgTuple.resname; - if (!loader.resources[resName]) - loader.add(resName,imgTuple.imgpath); + let resName = imgTuple.resname; + if (!loader.resources[resName]) loader.add(resName, imgTuple.imgpath); } - loader.load((loader,resources)=>{ - cb.call(ctx,loader,resources); - }); + loader.load((loader, resources) => { + cb.call(ctx, loader, resources); + }); } else { - window.setTimeout(()=>{ - if (Theatre.DEBUG) console.log("loader not done, waiting"); - this._getLoaderChainWait(this,imgSrcs,cb).call(this); - },200); + window.setTimeout(() => { + if (Theatre.DEBUG) console.log("loader not done, waiting"); + this._getLoaderChainWait(this, imgSrcs, cb).call(this); + }, 200); } - } - return func; + }; + return func; } /** * Given an array of theatreIds, stage them all * * @params ids (Array[(String)] : An array of theatreIds of inserts to load. - * @params cb (Function) : The function to invoke once the assets are loaded. + * @params cb (Function) : The function to invoke once the assets are loaded. */ - stageAllInserts(ids,cb) { - let actorId,params; - let imgSrcs = []; + stageAllInserts(ids, cb) { + let actorId, params; + let imgSrcs = []; for (let id of ids) { - actorId = id.replace("theatre-",""); - params = this._getInsertParamsFromActorId(actorId); - if (!params) continue; + actorId = id.replace("theatre-", ""); + params = this._getInsertParamsFromActorId(actorId); + if (!params) continue; // base insert - imgSrcs.push({imgpath: params.src, resname: params.src}); + imgSrcs.push({ imgpath: params.src, resname: params.src }); // load all rigging assets - let rigResources = Theatre.getActorRiggingResources(actorId); + let rigResources = Theatre.getActorRiggingResources(actorId); + + if (Theatre.DEBUG) console.log("RigResources for %s :", params.name, rigResources); - if (Theatre.DEBUG) console.log("RigResources for %s :",params.name,rigResources); - - for (let rigResource of rigResources) - imgSrcs.push({imgpath: rigResource.path, resname: rigResource.path}); + for (let rigResource of rigResources) imgSrcs.push({ imgpath: rigResource.path, resname: rigResource.path }); // load all emote base images + rigging for the emotes for (let emName in params.emotes) if (params.emotes[emName]) - if (params.emotes[emName].insert && params.emotes[emName].insert != "") - imgSrcs.push({imgpath: params.emotes[emName].insert, resname: params.emotes[emName].insert}); + if (params.emotes[emName].insert && params.emotes[emName].insert != "") + imgSrcs.push({ imgpath: params.emotes[emName].insert, resname: params.emotes[emName].insert }); } // load in the sprites - this._addSpritesToPixi(imgSrcs,cb); + this._addSpritesToPixi(imgSrcs, cb); } /** * "Stages" an insert by pre-loading the base + all emote images * * @params theatreId (String) : The theatreId of the insert to load. - * @params remote (Boolean) : Whether this is being invoked remotely or locally. + * @params remote (Boolean) : Whether this is being invoked remotely or locally. */ - stageInsertById(theatreId,remote) { - let actorId = theatreId.replace("theatre-",""); - let params = this._getInsertParamsFromActorId(actorId); + stageInsertById(theatreId, remote) { + let actorId = theatreId.replace("theatre-", ""); + let params = this._getInsertParamsFromActorId(actorId); if (!params) return; - //console.log("params: ",params); + //console.log("params: ",params); // kick asset loader to cache the portrait + emotes let imgSrcs = []; - //imgSrcs.push({imgpath: params.src, resname: `portrait-${theatreId}`}); + //imgSrcs.push({imgpath: params.src, resname: `portrait-${theatreId}`}); // get actor, load all emote images if (!params) { - console.log("ERROR: Actor does not exist for %s",actorId); - return null; + console.log("ERROR: Actor does not exist for %s", actorId); + return null; } - imgSrcs.push({imgpath: params.src, resname: params.src}); + imgSrcs.push({ imgpath: params.src, resname: params.src }); // load all rigging assets - let rigResources = Theatre.getActorRiggingResources(actorId); + let rigResources = Theatre.getActorRiggingResources(actorId); + + if (Theatre.DEBUG) console.log("RigResources for %s :", params.name, rigResources); - if (Theatre.DEBUG) console.log("RigResources for %s :",params.name,rigResources); - - for (let rigResource of rigResources) - imgSrcs.push({imgpath: rigResource.path, resname: rigResource.path}); + for (let rigResource of rigResources) imgSrcs.push({ imgpath: rigResource.path, resname: rigResource.path }); // load all emote base images + rigging for the emotes for (let emName in params.emotes) if (params.emotes[emName]) - if (params.emotes[emName].insert && params.emotes[emName].insert != "") - imgSrcs.push({imgpath: params.emotes[emName].insert, resname: params.emotes[emName].insert}); + if (params.emotes[emName].insert && params.emotes[emName].insert != "") + imgSrcs.push({ imgpath: params.emotes[emName].insert, resname: params.emotes[emName].insert }); // load in the sprites - this._addSpritesToPixi(imgSrcs,(loader, resources)=>{ - if (Theatre.DEBUG) console.log("staging complete for %s",theatreId,resources); - }); + this._addSpritesToPixi(imgSrcs, (loader, resources) => { + if (Theatre.DEBUG) console.log("staging complete for %s", theatreId, resources); + }); // Send socket event - if (!remote) - Theatre.instance._sendSceneEvent("stage",{insertid: theatreId}) + if (!remote) Theatre.instance._sendSceneEvent("stage", { insertid: theatreId }); } /** * Set the emote given the id * * @params ename (String) : The emote name. - * @params id (String) : The theatreId of the insert. - * @params remote (Boolean) : Wither this is being invoked remotely or locally. + * @params id (String) : The theatreId of the insert. + * @params remote (Boolean) : Wither this is being invoked remotely or locally. */ - setEmoteForInsertById(ename,id,remote) { + setEmoteForInsertById(ename, id, remote) { let insert = this.getInsertById(id); - this._setEmoteForInsert(ename,insert,remote); + this._setEmoteForInsert(ename, insert, remote); } /** * Set the emote given the name * * @params ename (String) : The emote name. - * @params name (String) : The label name of the insert. - * @params remote (Boolean) : Wither this is being invoked remotely or locally. + * @params name (String) : The label name of the insert. + * @params remote (Boolean) : Wither this is being invoked remotely or locally. */ - setEmoteForInsertByName(ename,name,remote) { + setEmoteForInsertByName(ename, name, remote) { let insert = this.getInsertByName(name); - this._setEmoteForInsert(ename,insert,remote); + this._setEmoteForInsert(ename, insert, remote); } /** * Set the emote given the insert * the moment the insert is in the RP bar * * @params ename (String) : The emote name. - * @params insert (Object) : An Object representing the insert. - * @params remote (Boolean) : Wither this is being invoked remotely or locally. + * @params insert (Object) : An Object representing the insert. + * @params remote (Boolean) : Wither this is being invoked remotely or locally. * * @private */ - _setEmoteForInsert(ename,insert,remote) { + _setEmoteForInsert(ename, insert, remote) { // given the emote name, get the image if possible, // and add it to the insert canvas. // @@ -3182,118 +3079,114 @@ class Theatre { // if the insert emote does not exist and the insert is // already either the base insert, or an emote without an // insert, do nothing - if (!insert) return; - let aEmote = insert.emote; - let actorId = insert.imgId.replace("theatre-",""); - let actor = game.actors.get(actorId); - if (!actor) return; + if (!insert) return; + let aEmote = insert.emote; + let actorId = insert.imgId.replace("theatre-", ""); + let actor = game.actors.get(actorId); + if (!actor) return; - let baseInsert = actor.data.img ? actor.data.img : "icons/mystery-man.png"; - if (actor.data.flags.theatre) - baseInsert = actor.data.flags.theatre.baseinsert ? actor.data.flags.theatre.baseinsert : baseInsert; - let emotes = Theatre.getActorEmotes(actorId); + let baseInsert = actor.data.img ? actor.data.img : "icons/mystery-man.png"; + if (actor.data.flags.theatre) baseInsert = actor.data.flags.theatre.baseinsert ? actor.data.flags.theatre.baseinsert : baseInsert; + let emotes = Theatre.getActorEmotes(actorId); // emote already active //if ((this.speakingAs != insert.imgId && !this.isDelayEmote) || this.delayedSentState > 2) - if (remote || !this.isDelayEmote) - if (aEmote == ename || (ename == null && aEmote == null)) return; + if (remote || !this.isDelayEmote) if (aEmote == ename || (ename == null && aEmote == null)) return; // if emote insert exists - let app = this.pixiCTX; - if (!!ename - && emotes[ename] - && emotes[ename].insert - && emotes[ename].insert != "") { + let app = this.pixiCTX; + if (!!ename && emotes[ename] && emotes[ename].insert && emotes[ename].insert != "") { // clear the pixi container - this._clearPortraitContainer(insert.imgId) + this._clearPortraitContainer(insert.imgId); // set this sprite to span the PIXI Container via _setupPortraitCanvas let imgSrcs = []; // emote base image - let emoteResName = emotes[ename].insert; - imgSrcs.push({imgpath: emotes[ename].insert, resname: emoteResName}); + let emoteResName = emotes[ename].insert; + imgSrcs.push({ imgpath: emotes[ename].insert, resname: emoteResName }); // add sprites this._addSpritesToPixi(imgSrcs, (loader, resources) => { - if (Theatre.DEBUG) console.log("emote insert loaded",resources); + if (Theatre.DEBUG) console.log("emote insert loaded", resources); // Error loading the sprite if (!resources[emoteResName] || resources[emoteResName].error) { - console.error("ERROR loading resource %s : %s : %s",insert.imgId,emoteResName,emotes[ename].insert); - ui.notifications.error(game.i18n.localize("Theatre.UI.Notification.ImageLoadFail_P1") + - + emoteResName - + game.i18n.localize("Theatre.UI.Notification.ImageLoadFail_P2") + emotes[ename].insert + "'"); - this.removeInsertById(insert.imgId); + console.error("ERROR loading resource %s : %s : %s", insert.imgId, emoteResName, emotes[ename].insert); + ui.notifications.error( + game.i18n.localize("Theatre.UI.Notification.ImageLoadFail_P1") + + +emoteResName + + game.i18n.localize("Theatre.UI.Notification.ImageLoadFail_P2") + + emotes[ename].insert + + "'" + ); + this.removeInsertById(insert.imgId); } // flag our insert with our emote state - insert.emote = ename; + insert.emote = ename; // now fix up the PIXI Container and make it pretty - this._setupPortraitContainer(insert.imgId,insert.optAlign,emoteResName,resources); + this._setupPortraitContainer(insert.imgId, insert.optAlign, emoteResName, resources); // re-attach label + typingBubble - insert.dockContainer.addChild(insert.label); - insert.dockContainer.addChild(insert.typingBubble); + insert.dockContainer.addChild(insert.label); + insert.dockContainer.addChild(insert.typingBubble); - this._repositionInsertElements(insert); + this._repositionInsertElements(insert); - if (!this.rendering) - this._renderTheatre(performance.now()); - }); + if (!this.rendering) this._renderTheatre(performance.now()); + }); } else { // load base insert unless the base insert is already loaded let loader = PIXI.Loader.shared; - let baseExists = false; + let baseExists = false; - this._clearPortraitContainer(insert.imgId) + this._clearPortraitContainer(insert.imgId); // flag our insert with our emote state, unless we're "actually" no emote rather // than just emoting with no insert available - if (ename) - insert.emote = ename; - else - insert.emote = null; + if (ename) insert.emote = ename; + else insert.emote = null; // if baseInsert is not present, put it in if (!loader.resources[baseInsert]) { - let imgSrcs = []; + let imgSrcs = []; // clear the PIXI Container - imgSrcs.push({imgpath: baseInsert, resname: baseInsert}); + imgSrcs.push({ imgpath: baseInsert, resname: baseInsert }); this._addSpritesToPixi(imgSrcs, (loader, resources) => { - if (Theatre.DEBUG) console.log("base insert re-loaded",resources); + if (Theatre.DEBUG) console.log("base insert re-loaded", resources); // Error loading the sprite if (!resources[baseInsert] || resources[baseInsert].error) { - console.error("ERROR loading resource %s : %s : %s",insert.imgId,baseInsert,baseInsert); - ui.notifications.error(game.i18n.localize("Theatre.UI.Notification.ImageLoadFail_P1") + - + baseInsert - + game.i18n.localize("Theatre.UI.Notification.ImageLoadFail_P2") + baseInsert + "'"); - this.removeInsertById(insert.imgId); + console.error("ERROR loading resource %s : %s : %s", insert.imgId, baseInsert, baseInsert); + ui.notifications.error( + game.i18n.localize("Theatre.UI.Notification.ImageLoadFail_P1") + + +baseInsert + + game.i18n.localize("Theatre.UI.Notification.ImageLoadFail_P2") + + baseInsert + + "'" + ); + this.removeInsertById(insert.imgId); } // now fix up the PIXI Container and make it pretty - this._setupPortraitContainer(insert.imgId,insert.optAlign,baseInsert,resources); + this._setupPortraitContainer(insert.imgId, insert.optAlign, baseInsert, resources); // re-attach label + typingBubble - insert.dockContainer.addChild(insert.label); - insert.dockContainer.addChild(insert.typingBubble); + insert.dockContainer.addChild(insert.label); + insert.dockContainer.addChild(insert.typingBubble); - this._repositionInsertElements(insert); + this._repositionInsertElements(insert); - if (!this.rendering) - this._renderTheatre(performance.now()); - }); + if (!this.rendering) this._renderTheatre(performance.now()); + }); } else { // base exists - this._setupPortraitContainer(insert.imgId,insert.optAlign,baseInsert,loader.resources); + this._setupPortraitContainer(insert.imgId, insert.optAlign, baseInsert, loader.resources); // re-attach label + typingBubble - insert.dockContainer.addChild(insert.label); - insert.dockContainer.addChild(insert.typingBubble); + insert.dockContainer.addChild(insert.label); + insert.dockContainer.addChild(insert.typingBubble); - this._repositionInsertElements(insert); + this._repositionInsertElements(insert); - if (!this.rendering) - this._renderTheatre(performance.now()); + if (!this.rendering) this._renderTheatre(performance.now()); } - } - } /** @@ -3304,11 +3197,9 @@ class Theatre { * @private */ _getTextBoxes() { - let textBoxes = []; - for (let container of this.theatreBar.children) - for (let textBox of container.children) - textBoxes.push(textBox); - return textBoxes; + let textBoxes = []; + for (let container of this.theatreBar.children) for (let textBox of container.children) textBoxes.push(textBox); + return textBoxes; } /** @@ -3317,12 +3208,14 @@ class Theatre { * @params id (String) : The theatreId of the insert/textbox * * @return (HTMLELement) : The HTMLElement which is the textbox, or undefined if it - * does not exist. + * does not exist. * * @private */ _getTextBoxById(id) { - return this._getTextBoxes().find(e=>{return e.getAttribute("imgId") == id}); + return this._getTextBoxes().find((e) => { + return e.getAttribute("imgId") == id; + }); } /** @@ -3331,55 +3224,57 @@ class Theatre { * @params id (String) : The label name of the insert/textbox * * @return (HTMLELement) : The HTMLElement which is the textbox, or undefined if it - * does not exist. + * does not exist. * * @private */ _getTextBoxByName(name) { - return this._getTextBoxes().find(e=>{return e.getAttribute("name") == name}); + return this._getTextBoxes().find((e) => { + return e.getAttribute("name") == name; + }); } /** * Add a textBox to the theatreBar * * @params textBox (HTMLElement) : The textBox to add to the theatreBar, - * MUST correspond to an insert. - * @params isLeft (Boolean) : Wither this textBox should be injected Left or Right. + * MUST correspond to an insert. + * @params isLeft (Boolean) : Wither this textBox should be injected Left or Right. * * @private */ - _addTextBoxToTheatreBar(textBox,isLeft) { - let textBoxes = this._getTextBoxes(); - let primeBar = document.getElementById("theatre-prime-bar"); - let secondBar = document.getElementById("theatre-second-bar"); + _addTextBoxToTheatreBar(textBox, isLeft) { + let textBoxes = this._getTextBoxes(); + let primeBar = document.getElementById("theatre-prime-bar"); + let secondBar = document.getElementById("theatre-second-bar"); if (textBoxes.length == 0) { // no dock // 1. slide in prime container, add textBox to it - primeBar.appendChild(textBox); - primeBar.style.left = "0%"; - primeBar.style.opacity = "1"; - primeBar.style["pointer-events"] = "all"; - this.theatreBar.style.opacity = "1"; - Hooks.call("theatreDockActive",this.dockActive); + primeBar.appendChild(textBox); + primeBar.style.left = "0%"; + primeBar.style.opacity = "1"; + primeBar.style["pointer-events"] = "all"; + this.theatreBar.style.opacity = "1"; + Hooks.call("theatreDockActive", this.dockActive); } else if (textBoxes.length == 1) { // single dock // 1. slide in second container, and add new textBox to it - let insert = this.getInsertById(textBox.getAttribute("imgId")); + let insert = this.getInsertById(textBox.getAttribute("imgId")); if (insert) { //insert.meta.fromPrime = true; - insert.nameOrientation = "right"; + insert.nameOrientation = "right"; } - let dualWidth = Math.min(Math.floor(this.theatreBar.offsetWidth/2),650); - secondBar.style.left = `calc(100% - ${dualWidth}px)`; - secondBar.style.opacity = "1"; - secondBar.style["pointer-events"] = "all"; - secondBar.style.width = `${dualWidth}px`; - primeBar.style.width = `${dualWidth}px`; + let dualWidth = Math.min(Math.floor(this.theatreBar.offsetWidth / 2), 650); + secondBar.style.left = `calc(100% - ${dualWidth}px)`; + secondBar.style.opacity = "1"; + secondBar.style["pointer-events"] = "all"; + secondBar.style.width = `${dualWidth}px`; + primeBar.style.width = `${dualWidth}px`; - secondBar.appendChild(textBox); - Hooks.call("theatreDockActive",this.dockActive); + secondBar.appendChild(textBox); + Hooks.call("theatreDockActive", this.dockActive); } else if (textBoxes.length == 2) { // dual docks // 1. confirm if we're in dual dock mode @@ -3388,29 +3283,27 @@ class Theatre { // the 'prime' dock, and add them to the prime dock (should be one) // 3. expand the prime dock to fit the max bar width for (let sbb of secondBar.children) { - let insert = this.getInsertById(sbb.getAttribute("imgId")); + let insert = this.getInsertById(sbb.getAttribute("imgId")); if (insert) { //insert.meta.fromSecond = true; - insert.nameOrientation = "left"; + insert.nameOrientation = "left"; } - primeBar.appendChild(sbb); + primeBar.appendChild(sbb); } secondBar.style.left = "200%"; - secondBar.style.opacity = "0"; - secondBar.style["pointer-events"] = "none"; - primeBar.style.width = "100%"; - - if (isLeft) KHelpers.insertBefore(textBox,primeBar.children[0]); - else primeBar.appendChild(textBox); - Hooks.call("theatreDockActive",this.dockActive); - - } else if (textBoxes.length > 2){ + secondBar.style.opacity = "0"; + secondBar.style["pointer-events"] = "none"; + primeBar.style.width = "100%"; + + if (isLeft) KHelpers.insertBefore(textBox, primeBar.children[0]); + else primeBar.appendChild(textBox); + Hooks.call("theatreDockActive", this.dockActive); + } else if (textBoxes.length > 2) { // bar dock // 1. Just find the prime container, and add the new textBox to it - if (isLeft) KHelpers.insertBefore(textBox,primeBar.children[0]); - else primeBar.appendChild(textBox); - Hooks.call("theatreDockActive",this.dockActive); - + if (isLeft) KHelpers.insertBefore(textBox, primeBar.children[0]); + else primeBar.appendChild(textBox); + Hooks.call("theatreDockActive", this.dockActive); } } @@ -3418,28 +3311,28 @@ class Theatre { * Remove a textBox from the theatreBar * * @param textBox (HTMLElement : div) : the textBox to add to the theatreBar, - * MUST correspond to an insert. + * MUST correspond to an insert. * * @private */ _removeTextBoxFromTheatreBar(textBox) { - let textBoxes = this._getTextBoxes(); - let primeBar = document.getElementById("theatre-prime-bar"); - let secondBar = document.getElementById("theatre-second-bar"); + let textBoxes = this._getTextBoxes(); + let primeBar = document.getElementById("theatre-prime-bar"); + let secondBar = document.getElementById("theatre-second-bar"); if (textBoxes.length == 0) { // no dock // Should be impossible - console.log("REMOVE TEXTBOX ERROR, NO TEXTBOXES",textBox,this.theatreBar); + console.log("REMOVE TEXTBOX ERROR, NO TEXTBOXES", textBox, this.theatreBar); } else if (textBoxes.length == 1) { // single dock // 1. Remove the text Box, and close the primary bar primeBar.style.left = "-100%"; - primeBar.style.opacity = "0"; - primeBar.style["pointer-events"] = "none"; - textBox.parentNode.removeChild(textBox); - this.theatreBar.style.opacity = "0"; - Hooks.call("theatreDockActive",this.dockActive); + primeBar.style.opacity = "0"; + primeBar.style["pointer-events"] = "none"; + textBox.parentNode.removeChild(textBox); + this.theatreBar.style.opacity = "0"; + Hooks.call("theatreDockActive", this.dockActive); } else if (textBoxes.length == 2) { // dual docks // 1. confirm if we're in dual dock mode @@ -3450,208 +3343,201 @@ class Theatre { // then add the textBoxes in the 'secondary' dock to the primary. for (let sbb of secondBar.children) { if (sbb.getAttribute("imgId") != textBox.getAttribute("imgId")) { - let insert = this.getInsertById(sbb.getAttribute("imgId")); + let insert = this.getInsertById(sbb.getAttribute("imgId")); if (insert) { //insert.meta.fromSecond = true; - insert.nameOrientation = "left"; + insert.nameOrientation = "left"; } - primeBar.appendChild(sbb); + primeBar.appendChild(sbb); } } - secondBar.style.left = "200%"; - secondBar.style.opacity = "0"; - secondBar.style["pointer-events"] = "none"; + secondBar.style.left = "200%"; + secondBar.style.opacity = "0"; + secondBar.style["pointer-events"] = "none"; primeBar.style.width = "750px"; - textBox.parentNode.removeChild(textBox); - Hooks.call("theatreDockActive",this.dockActive); - - } else if (textBoxes.length == 3){ + textBox.parentNode.removeChild(textBox); + Hooks.call("theatreDockActive", this.dockActive); + } else if (textBoxes.length == 3) { // bar dock - // 1. create the dual docks - for (let idx=primeBar.children.length-1; idx>=0; --idx) { + // 1. create the dual docks + for (let idx = primeBar.children.length - 1; idx >= 0; --idx) { if (primeBar.children[idx].getAttribute("imgId") != textBox.getAttribute("imgId")) { - let insert = this.getInsertById(primeBar.children[idx].getAttribute("imgId")); + let insert = this.getInsertById(primeBar.children[idx].getAttribute("imgId")); if (insert) { //insert.meta.fromPrime = true; - insert.nameOrientation = "right"; + insert.nameOrientation = "right"; } - secondBar.appendChild(primeBar.children[idx]); - break; + secondBar.appendChild(primeBar.children[idx]); + break; } } - let dualWidth = Math.min(Math.floor(this.theatreBar.offsetWidth/2),650); - secondBar.style.left = `calc(100% - ${dualWidth}px)`; - secondBar.style.opacity = "1"; - secondBar.style["pointer-events"] = "all"; - secondBar.style.width = `${dualWidth}px`; - primeBar.style.width = `${dualWidth}px`; - - textBox.parentNode.removeChild(textBox); - Hooks.call("theatreDockActive",this.dockActive); + let dualWidth = Math.min(Math.floor(this.theatreBar.offsetWidth / 2), 650); + secondBar.style.left = `calc(100% - ${dualWidth}px)`; + secondBar.style.opacity = "1"; + secondBar.style["pointer-events"] = "all"; + secondBar.style.width = `${dualWidth}px`; + primeBar.style.width = `${dualWidth}px`; + + textBox.parentNode.removeChild(textBox); + Hooks.call("theatreDockActive", this.dockActive); } else { // normal bar removal - textBox.parentNode.removeChild(textBox); - Hooks.call("theatreDockActive",this.dockActive); + textBox.parentNode.removeChild(textBox); + Hooks.call("theatreDockActive", this.dockActive); } } /** * Given an image, path, attempt to inject it on the left * - * @params imgPath (String) : The path to the image that will be used for the initial portrait. + * @params imgPath (String) : The path to the image that will be used for the initial portrait. * @params portName (String) : The name that will be applied to the portrait's label. * @params ImgId (String) : The theatreId that will be assigned to this insert (must be "theatre-") - * @params optAlign (String) : The alignment mode to use. Currently only "top" and "bottom" are accepted. - * @params emotions (Object) : An Object containing the emote states to launch with. - * @params remote (Boolean) : Boolean indicating if this is being invoked remotely, or locally. + * @params optAlign (String) : The alignment mode to use. Currently only "top" and "bottom" are accepted. + * @params emotions (Object) : An Object containing the emote states to launch with. + * @params remote (Boolean) : Boolean indicating if this is being invoked remotely, or locally. */ - injectLeftPortrait(imgPath,portName,imgId,optAlign,emotions,remote) { + injectLeftPortrait(imgPath, portName, imgId, optAlign, emotions, remote) { if (!!this.getInsertById(imgId)) { - console.log('ID "%s" already exists! Refusing to inject %s',imgId,portName); - return; + console.log('ID "%s" already exists! Refusing to inject %s', imgId, portName); + return; } if (this.portraitDocks.length == 1) { // inject Right instread - this.injectRightPortrait(imgPath,portName,imgId,optAlign,emotions,remote); - return; + this.injectRightPortrait(imgPath, portName, imgId, optAlign, emotions, remote); + return; } // activate in navbar if not already let navItem = this.getNavItemById(imgId); - if (navItem) - KHelpers.addClass(navItem,"theatre-control-nav-bar-item-active"); + if (navItem) KHelpers.addClass(navItem, "theatre-control-nav-bar-item-active"); - let dock = this._createPortraitPIXIContainer(imgPath,portName,imgId,optAlign,emotions,true); + let dock = this._createPortraitPIXIContainer(imgPath, portName, imgId, optAlign, emotions, true); let textBox = document.createElement("div"); // textBox class + style depends on our display mode switch (this.settings.theatreStyle) { case "lightbox": - KHelpers.addClass(textBox,"theatre-text-box-light"); - break; + KHelpers.addClass(textBox, "theatre-text-box-light"); + break; case "clearbox": - KHelpers.addClass(textBox,"theatre-text-box-clear"); - break; + KHelpers.addClass(textBox, "theatre-text-box-clear"); + break; case "mangabubble": - break; + break; case "textbox": default: - KHelpers.addClass(textBox,"theatre-text-box"); - break; + KHelpers.addClass(textBox, "theatre-text-box"); + break; } - KHelpers.addClass(textBox,"no-scrollbar"); + KHelpers.addClass(textBox, "no-scrollbar"); - portName = portName.toLowerCase(); - textBox.setAttribute('name',portName); - textBox.setAttribute("imgid",imgId); - textBox.style.opacity = "0"; - this._applyFontFamily(textBox,this.textFont); + portName = portName.toLowerCase(); + textBox.setAttribute("name", portName); + textBox.setAttribute("imgid", imgId); + textBox.style.opacity = "0"; + this._applyFontFamily(textBox, this.textFont); - textBox.addEventListener("mousedown",this.handleTextBoxMouseDown); - textBox.addEventListener("mouseup",this.handleTextBoxMouseUp); - textBox.addEventListener("dblclick",this.handleTextBoxMouseDoubleClick); + textBox.addEventListener("mousedown", this.handleTextBoxMouseDown); + textBox.addEventListener("mouseup", this.handleTextBoxMouseUp); + textBox.addEventListener("dblclick", this.handleTextBoxMouseDoubleClick); // NOTE: we leave insert container positioning up to reorderInserts // which will fire when the loader processes it for injection - this._addTextBoxToTheatreBar(textBox,true); + this._addTextBoxToTheatreBar(textBox, true); // Push to socket our event - if (!remote) - this._sendSceneEvent("enterscene",{insertid: imgId, emotions: emotions, isleft: true}); + if (!remote) this._sendSceneEvent("enterscene", { insertid: imgId, emotions: emotions, isleft: true }); } /** * Given an image, path, attempt to inject it on the right * - * @params imgPath (String) : The path to the image that will be used for the initial portrait. + * @params imgPath (String) : The path to the image that will be used for the initial portrait. * @params portName (String) : The name that will be applied to the portrait's label. * @params ImgId (String) : The theatreId that will be assigned to this insert (must be "theatre-") - * @params optAlign (String) : The alignment mode to use. Currently only "top" and "bottom" are accepted. - * @params emotions (Object) : An Object containing the emote states to launch with. - * @params remote (Boolean) : Boolean indicating if this is being invoked remotely, or locally. + * @params optAlign (String) : The alignment mode to use. Currently only "top" and "bottom" are accepted. + * @params emotions (Object) : An Object containing the emote states to launch with. + * @params remote (Boolean) : Boolean indicating if this is being invoked remotely, or locally. */ - injectRightPortrait(imgPath,portName,imgId,optAlign,emotions,remote) { + injectRightPortrait(imgPath, portName, imgId, optAlign, emotions, remote) { if (!!this.getInsertById(imgId)) { - console.log('ID "%s" already exists! Refusing to inject %s',imgId,portName); - return; + console.log('ID "%s" already exists! Refusing to inject %s', imgId, portName); + return; } if (this.portraitDocks.length == 0) { // inject Left instread - this.injectLeftPortrait(imgPath,portName,imgId,optAlign,emotions,remote); - return; + this.injectLeftPortrait(imgPath, portName, imgId, optAlign, emotions, remote); + return; } // activate in navbar if not already let navItem = this.getNavItemById(imgId); - if (navItem) - KHelpers.addClass(navItem,"theatre-control-nav-bar-item-active"); + if (navItem) KHelpers.addClass(navItem, "theatre-control-nav-bar-item-active"); - let dock = this._createPortraitPIXIContainer(imgPath,portName,imgId,optAlign,emotions,false); - let textBox = document.createElement("div"); + let dock = this._createPortraitPIXIContainer(imgPath, portName, imgId, optAlign, emotions, false); + let textBox = document.createElement("div"); // textBox class + style depends on our display mode switch (this.settings.theatreStyle) { case "lightbox": - KHelpers.addClass(textBox,"theatre-text-box-light"); - break; + KHelpers.addClass(textBox, "theatre-text-box-light"); + break; case "clearbox": - KHelpers.addClass(textBox,"theatre-text-box-clear"); - break; + KHelpers.addClass(textBox, "theatre-text-box-clear"); + break; case "mangabubble": - break; + break; case "textbox": default: - KHelpers.addClass(textBox,"theatre-text-box"); - break; + KHelpers.addClass(textBox, "theatre-text-box"); + break; } - KHelpers.addClass(textBox,"no-scrollbar"); + KHelpers.addClass(textBox, "no-scrollbar"); - portName = portName.toLowerCase(); - textBox.setAttribute('name',portName); - textBox.setAttribute("imgid",imgId); - textBox.style.opacity = "0"; - this._applyFontFamily(textBox,this.textFont); + portName = portName.toLowerCase(); + textBox.setAttribute("name", portName); + textBox.setAttribute("imgid", imgId); + textBox.style.opacity = "0"; + this._applyFontFamily(textBox, this.textFont); - textBox.addEventListener("mousedown",this.handleTextBoxMouseDown); - textBox.addEventListener("mouseup",this.handleTextBoxMouseUp); - textBox.addEventListener("dblclick",this.handleTextBoxMouseDoubleClick); + textBox.addEventListener("mousedown", this.handleTextBoxMouseDown); + textBox.addEventListener("mouseup", this.handleTextBoxMouseUp); + textBox.addEventListener("dblclick", this.handleTextBoxMouseDoubleClick); - this._addTextBoxToTheatreBar(textBox); + this._addTextBoxToTheatreBar(textBox); // Push to socket our event - if (!remote) - this._sendSceneEvent("enterscene",{insertid: imgId, emotions: emotions, isleft: false}); + if (!remote) this._sendSceneEvent("enterscene", { insertid: imgId, emotions: emotions, isleft: false }); } /** * Removes insert by ID * * @params id (String) : The theatreId of the insert to remove. - * @params remote (Boolean) : Boolean indicating if this is being invoked remotely, or locally. + * @params remote (Boolean) : Boolean indicating if this is being invoked remotely, or locally. * * @return (Object) : An object containing the items that were removed {insert : (Object), textBox: (HTMLElement)} - * or null if there was nothing to remove. + * or null if there was nothing to remove. */ - removeInsertById(id,remote) { - name = name.toLowerCase(); - let toRemoveInsert, - toRemoveTextBox; + removeInsertById(id, remote) { + name = name.toLowerCase(); + let toRemoveInsert, toRemoveTextBox; for (let insert of this.portraitDocks) { if (insert.imgId == id && !insert.deleting) { - insert.deleting = true; - toRemoveInsert = insert; - break; + insert.deleting = true; + toRemoveInsert = insert; + break; } } for (let textBox of this._getTextBoxes()) { if (textBox.getAttribute("imgId") == id && !!!textBox.getAttribute("deleting")) { - textBox.setAttribute("deleting",true); - toRemoveTextBox = textBox - break; + textBox.setAttribute("deleting", true); + toRemoveTextBox = textBox; + break; } } - if (!!!toRemoveInsert || !!!toRemoveTextBox) - return null; + if (!!!toRemoveInsert || !!!toRemoveTextBox) return null; - return this._removeInsert(toRemoveInsert,toRemoveTextBox,remote); + return this._removeInsert(toRemoveInsert, toRemoveTextBox, remote); } /** @@ -3660,38 +3546,37 @@ class Theatre { * and removed. * * @params name (String) : The label name of the insert to remove. - * @params remote (Boolean) : Boolean indicating if this is being invoked remotely, or locally. + * @params remote (Boolean) : Boolean indicating if this is being invoked remotely, or locally. * * @return (Object) : An object containing the items that were removed {insert : (Object), textBox: (HTMLElement)} - * or null if there was nothing to remove. + * or null if there was nothing to remove. */ - removeInsertByName(name,remote) { - name = name.toLowerCase(); + removeInsertByName(name, remote) { + name = name.toLowerCase(); let id = null, - toRemoveInsert, - toRemoveTextBox; + toRemoveInsert, + toRemoveTextBox; for (let insert of this.portraitDocks) { if (insert.name == name && !insert.deleting) { - id = insert.imgId; - //insert.parentNode.removeChild(insert); - insert.deleting = true; - toRemoveInsert = insert; - break; + id = insert.imgId; + //insert.parentNode.removeChild(insert); + insert.deleting = true; + toRemoveInsert = insert; + break; } } - if (!id) return; + if (!id) return; for (let textBox of this._getTextBoxes()) { if (textBox.getAttribute("imgId") == id && !!!textBox.getAttribute("deleting")) { - //textBox.parentNode.removeChild(textBox); - textBox.setAttribute("deleting",true); - toRemoveTextBox = textBox - break; + //textBox.parentNode.removeChild(textBox); + textBox.setAttribute("deleting", true); + toRemoveTextBox = textBox; + break; } } - if (!!!toRemoveInsert || !!!toRemoveTextBox) - return null; + if (!!!toRemoveInsert || !!!toRemoveTextBox) return null; - return this._removeInsert(toRemoveInsert,toRemoveTextBox,remote); + return this._removeInsert(toRemoveInsert, toRemoveTextBox, remote); } /** @@ -3699,132 +3584,126 @@ class Theatre { * * @params toRemoveInsert (Object) : An Object representing the insert to be removed. * @params toRemoveTextBox (HTMLElement) : The textbox of the insert to be removed. - * @params remote (Boolean) : Boolean indicating if this is being invoked remotely, or locally. + * @params remote (Boolean) : Boolean indicating if this is being invoked remotely, or locally. * * @return (Object) : An object containing the items that were removed {insert : (Object), textBox: (HTMLElement)} - * or null if there was nothing to remove. + * or null if there was nothing to remove. * * @private */ - _removeInsert(toRemoveInsert,toRemoveTextBox,remote) { - let isOwner = this.isActorOwner(game.user.id,toRemoveInsert.imgId); + _removeInsert(toRemoveInsert, toRemoveTextBox, remote) { + let isOwner = this.isActorOwner(game.user.id, toRemoveInsert.imgId); // permission check if (!remote && !isOwner) { ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.DoNotControl")); - return null; + return null; } if (toRemoveInsert.decayTOId) { - window.clearTimeout(toRemoveInsert.decayTOId); - toRemoveInsert.decayTOId = null; + window.clearTimeout(toRemoveInsert.decayTOId); + toRemoveInsert.decayTOId = null; } - // Save configuration if this is not a remote operation, and we're the owners of this + // Save configuration if this is not a remote operation, and we're the owners of this // insert if (!remote && isOwner) { - let actorId = toRemoveInsert.imgId.replace("theatre-",""); - let actor = game.actors.get(actorId); + let actorId = toRemoveInsert.imgId.replace("theatre-", ""); + let actor = game.actors.get(actorId); if (actor) { - let skel = {}; - skel["flags.theatre.settings.emote"] = toRemoveInsert.emote; - skel["flags.theatre.settings.textflyin"] = toRemoveInsert.textFlyin; - skel["flags.theatre.settings.textstanding"] = toRemoveInsert.textStanding; - skel["flags.theatre.settings.textfont"] = toRemoveInsert.textFont; - skel["flags.theatre.settings.textsize"] = toRemoveInsert.textSize; - skel["flags.theatre.settings.textcolor"] = toRemoveInsert.textColor; - actor.update(skel).then((response)=>{ - if (Theatre.DEBUG) console.log("updated with resp: ",response); - }); + let skel = {}; + skel["flags.theatre.settings.emote"] = toRemoveInsert.emote; + skel["flags.theatre.settings.textflyin"] = toRemoveInsert.textFlyin; + skel["flags.theatre.settings.textstanding"] = toRemoveInsert.textStanding; + skel["flags.theatre.settings.textfont"] = toRemoveInsert.textFont; + skel["flags.theatre.settings.textsize"] = toRemoveInsert.textSize; + skel["flags.theatre.settings.textcolor"] = toRemoveInsert.textColor; + actor.update(skel).then((response) => { + if (Theatre.DEBUG) console.log("updated with resp: ", response); + }); } } // animate and delayed removal - //let isLeft = toRemoveInsert.getElementsByClassName("theatre-portrait-left").length > 0; - let exitX = 0; + //let isLeft = toRemoveInsert.getElementsByClassName("theatre-portrait-left").length > 0; + let exitX = 0; if (toRemoveInsert.portrait) { if (toRemoveInsert.exitOrientation == "left") { - exitX = toRemoveInsert.dockContainer.x - toRemoveInsert.portrait.width + exitX = toRemoveInsert.dockContainer.x - toRemoveInsert.portrait.width; } else { - exitX = toRemoveInsert.dockContainer.x + toRemoveInsert.portrait.width + exitX = toRemoveInsert.dockContainer.x + toRemoveInsert.portrait.width; } } // Push to socket our event - if (!remote) - this._sendSceneEvent("exitscene",{insertid: toRemoveInsert.imgId}); + if (!remote) this._sendSceneEvent("exitscene", { insertid: toRemoveInsert.imgId }); // unactivate from navbar - for(let navItem of this.theatreNavBar.children) + for (let navItem of this.theatreNavBar.children) if (navItem.getAttribute("imgId") == toRemoveInsert.imgId) { - KHelpers.removeClass(navItem,"theatre-control-nav-bar-item-active"); - if (toRemoveInsert.imgId == this.speakingAs) - KHelpers.removeClass(navItem,"theatre-control-nav-bar-item-speakingas"); + KHelpers.removeClass(navItem, "theatre-control-nav-bar-item-active"); + if (toRemoveInsert.imgId == this.speakingAs) KHelpers.removeClass(navItem, "theatre-control-nav-bar-item-speakingas"); } // clear chat cover + effects if active for this ID if (this.speakingAs == toRemoveInsert.imgId) { - let cimg = this.getTheatreCoverPortrait(); - cimg.removeAttribute("src"); - cimg.style.opacity = "0"; - let label = this._getLabelFromInsert(toRemoveInsert); - TweenMax.killTweensOf(label); + let cimg = this.getTheatreCoverPortrait(); + cimg.removeAttribute("src"); + cimg.style.opacity = "0"; + let label = this._getLabelFromInsert(toRemoveInsert); + TweenMax.killTweensOf(label); // clear typing for (let userId in this.usersTyping) - if (this.usersTyping[userId] && (this.usersTyping[userId].theatreId == toRemoveInsert.imgId)) { - this.removeUserTyping(userId); - this.usersTyping[userId] = null; - break; + if (this.usersTyping[userId] && this.usersTyping[userId].theatreId == toRemoveInsert.imgId) { + this.removeUserTyping(userId); + this.usersTyping[userId] = null; + break; } // clear label // clear speakingAs this.speakingAs = null; - this.renderEmoteMenu(); + this.renderEmoteMenu(); } // kill any animations of textBox for (let c of toRemoveTextBox.children) { - for (let sc of c.children) - TweenMax.killTweensOf(sc); - TweenMax.killTweensOf(c); + for (let sc of c.children) TweenMax.killTweensOf(sc); + TweenMax.killTweensOf(c); } - TweenMax.killTweensOf(toRemoveTextBox); + TweenMax.killTweensOf(toRemoveTextBox); /* for (let c of toRemoveTextBox.children) c.parentNode.removeChild(c); */ // fade away text box - toRemoveTextBox.style.opacity = 0; + toRemoveTextBox.style.opacity = 0; // animate away the dockContainer - let tweenId = "containerSlide"; - let tween = TweenMax.to(toRemoveInsert.dockContainer,1,{ + let tweenId = "containerSlide"; + let tween = TweenMax.to(toRemoveInsert.dockContainer, 1, { //delay: 0.5, - pixi:{x: exitX, alpha: 0}, + pixi: { x: exitX, alpha: 0 }, ease: Power4.easeOut, - onComplete: function(ctx,imgId,tweenId) { + onComplete: function (ctx, imgId, tweenId) { // decrement the rendering accumulator - ctx._removeDockTween(imgId,this,tweenId); + ctx._removeDockTween(imgId, this, tweenId); // remove our own reference from the dockContainer tweens }, - onCompleteParams: [this,toRemoveInsert.imgId,tweenId], - }); - this._addDockTween(toRemoveInsert.imgId,tween,tweenId); - - - window.setTimeout(()=>{ - this._destroyPortraitDock(toRemoveInsert.imgId) - this._removeTextBoxFromTheatreBar(toRemoveTextBox); + onCompleteParams: [this, toRemoveInsert.imgId, tweenId], + }); + this._addDockTween(toRemoveInsert.imgId, tween, tweenId); - if (this.reorderTOId) - window.clearTimeout(this.reorderTOId) + window.setTimeout(() => { + this._destroyPortraitDock(toRemoveInsert.imgId); + this._removeTextBoxFromTheatreBar(toRemoveTextBox); - this.reorderTOId = window.setTimeout(()=>{ - Theatre.reorderInserts(); - this.reorderTOId = null; - },750); + if (this.reorderTOId) window.clearTimeout(this.reorderTOId); - },1000); + this.reorderTOId = window.setTimeout(() => { + Theatre.reorderInserts(); + this.reorderTOId = null; + }, 750); + }, 1000); // return results of what was removed - return {insert: toRemoveInsert, textBox: toRemoveTextBox}; + return { insert: toRemoveInsert, textBox: toRemoveTextBox }; } /** @@ -3835,33 +3714,31 @@ class Theatre { * @return (Number) : The number of inserts in the dock */ get dockActive() { - return this.portraitDocks.length; + return this.portraitDocks.length; } /** * Get nav item by ID * - * @params id (String) : The theatreId insert whose navItem we want. + * @params id (String) : The theatreId insert whose navItem we want. * - * @return (HTMLElement) : The nav item, if found, else undefined. + * @return (HTMLElement) : The nav item, if found, else undefined. */ getNavItemById(id) { const theatreActor = this.stage[id]; - if (theatreActor) - return theatreActor.navElement; + if (theatreActor) return theatreActor.navElement; } /** * Get nav item by Name * - * @params name (String) : The label name of the insert whose navItem we want. + * @params name (String) : The label name of the insert whose navItem we want. * - * @return (HTMLElement) : The nav item, if found, else undefined. + * @return (HTMLElement) : The nav item, if found, else undefined. */ getNavItemByName(name) { for (let navItem of this.theatreNavBar.children) { - if (navItem.getAttribute("name") == name) - return navItem; + if (navItem.getAttribute("name") == name) return navItem; } } @@ -3870,15 +3747,14 @@ class Theatre { * * @params id (String) : The theatreId of an insert whose textBox we want. * - * @return (HTMLElement) : The TextBox of the given theatreId, or undefined. + * @return (HTMLElement) : The TextBox of the given theatreId, or undefined. */ getTextBoxById(id) { // Narrator is a special case - if (id == Theatre.NARRATOR) - return this.theatreNarrator.getElementsByClassName("theatre-narrator-content")[0]; + if (id == Theatre.NARRATOR) return this.theatreNarrator.getElementsByClassName("theatre-narrator-content")[0]; for (let textBox of this._getTextBoxes()) { if (textBox.getAttribute("imgId") == id) { - return textBox; + return textBox; } } } @@ -3888,14 +3764,13 @@ class Theatre { * * @params name (String) : The label name of an insert whose textBox we want. * - * @return (HTMLElement) : The TextBox of the given theatreId, or undefined. + * @return (HTMLElement) : The TextBox of the given theatreId, or undefined. */ getTextBoxByName(name) { - if (name == Theatre.NARRATOR) - return this.theatreNarrator.getElementsByClassName("theatre-narrator-content")[0]; + if (name == Theatre.NARRATOR) return this.theatreNarrator.getElementsByClassName("theatre-narrator-content")[0]; for (let textBox of this._getTextBoxes()) { if (textBox.getAttribute("name") == name) { - return textBox; + return textBox; } } } @@ -3908,13 +3783,12 @@ class Theatre { * @return (Object) : The Object representing the insert, or undefined. */ getInsertById(id) { - for (let idx=this.portraitDocks.length-1; idx>=0; --idx) + for (let idx = this.portraitDocks.length - 1; idx >= 0; --idx) if (this.portraitDocks[idx].imgId == id) { - if (this.portraitDocks[idx].dockContainer) - return this.portraitDocks[idx]; + if (this.portraitDocks[idx].dockContainer) return this.portraitDocks[idx]; else { - this.portraitDocks.splice(idx,1); - return undefined; + this.portraitDocks.splice(idx, 1); + return undefined; } } } @@ -3927,13 +3801,12 @@ class Theatre { * @return (Object) : The Object representing the insert, or undefined. */ getInsertByName(name) { - for (let idx=this.portraitDocks.length-1; idx>=0; --idx) + for (let idx = this.portraitDocks.length - 1; idx >= 0; --idx) if (this.portraitDocks[idx].name == name) { - if (this.portraitDocks[idx].dockContainer) - return this.portraitDocks[idx]; + if (this.portraitDocks[idx].dockContainer) return this.portraitDocks[idx]; else { - this.portraitDocks.splice(idx,1); - return undefined; + this.portraitDocks.splice(idx, 1); + return undefined; } } } @@ -3943,13 +3816,13 @@ class Theatre { * * @params insert (Object) : The Object representing the insert. * - * @return (Object PIXISprite) : The PIXISprite portrait of the insert. + * @return (Object PIXISprite) : The PIXISprite portrait of the insert. * * @private */ _getPortraitSpriteFromInsert(insert) { - if (!insert || !insert.dockContainer || !insert.potrrait) return null; - return insert.portrait; + if (!insert || !insert.dockContainer || !insert.potrrait) return null; + return insert.portrait; } /** @@ -3962,8 +3835,8 @@ class Theatre { * @private */ _getPortraitContainerFromInsert(insert) { - if (!insert || !insert.dockContainer) return null; - return insert.portraitContainer; + if (!insert || !insert.dockContainer) return null; + return insert.portraitContainer; } /** @@ -3971,101 +3844,93 @@ class Theatre { * * @params insert (Object) : The Object representing the insert. * - * @return (Object PIXIText) : The PIXIText label of the insert. + * @return (Object PIXIText) : The PIXIText label of the insert. * * @private */ _getLabelFromInsert(insert) { - if (!insert || !insert.dockContainer) return null; - return insert.label; + if (!insert || !insert.dockContainer) return null; + return insert.label; } /** * Gets the theatre's chat cover image * * @return (HTMLElement) : The tag of the cover portrait in the - * chat message area. + * chat message area. */ getTheatreCoverPortrait() { - return this.theatreChatCover.getElementsByTagName("img")[0]; + return this.theatreChatCover.getElementsByTagName("img")[0]; } /** * Get speaking insert of /this/ user * * @return (Object) : The Object representing the insert that this - * User is speaking as, else undefined. + * User is speaking as, else undefined. */ getSpeakingInsert() { - let insert = this.getInsertById(this.speakingAs); - return insert; + let insert = this.getInsertById(this.speakingAs); + return insert; } /** * Get speaking name of /this/ user * * @return (Object PIXISprite) : The PIXISrite label of the insert the - * User is speaking as, else undefined. + * User is speaking as, else undefined. */ getSpeakingLabel() { - let insert = this.getInsertById(this.speakingAs); - return this._getLabelFromInsert(insert); + let insert = this.getInsertById(this.speakingAs); + return this._getLabelFromInsert(insert); } /** * Get speaking portrait container of /this/ user * - * @return (Object PIXIContainer) : The PIXIContainer portrait container - * of the insert the User is speaking as, else undefined. + * @return (Object PIXIContainer) : The PIXIContainer portrait container + * of the insert the User is speaking as, else undefined. */ getSpeakingPortraitContainer() { - let insert = this.getInsertById(this.speakingAs); - return this._getPortraitContainerFromInsert(insert); + let insert = this.getInsertById(this.speakingAs); + return this._getPortraitContainerFromInsert(insert); } /** * Get speaking textBox of /this/ user * * @return (HTMLElement) : The textBox of the insert the User is - * speaking as, else undefined. + * speaking as, else undefined. */ getSpeakingTextBox() { - return this._getTextBoxById(this.speakingAs); + return this._getTextBoxById(this.speakingAs); } - /** * Swap Inserts by ID * * @params id1 (String) : The theatreId of the first insert to swap. * @params id2 (String) : The theatreId of the second insert to swap. - * @params remote (Boolean) : Wither this is being invoked remotely, or locally. + * @params remote (Boolean) : Wither this is being invoked remotely, or locally. */ - swapInsertsById(id1,id2,remote) { - if (this.portraitDocks.length < 2) return; + swapInsertsById(id1, id2, remote) { + if (this.portraitDocks.length < 2) return; - let insert1, - insert2, - textBox1, - textBox2; + let insert1, insert2, textBox1, textBox2; for (let insert of this.portraitDocks) { - if (insert.imgId == id1 && !!!insert1) - insert1 = insert; - else if (insert.imgId == id2 && !!!insert2) - insert2 = insert; - if (!!insert1 && !!insert2) break; + if (insert.imgId == id1 && !!!insert1) insert1 = insert; + else if (insert.imgId == id2 && !!!insert2) insert2 = insert; + if (!!insert1 && !!insert2) break; } for (let textBox of this._getTextBoxes()) { - if (textBox.getAttribute("imgId") == id1 && !!!textBox1) - textBox1 = textBox; - else if (textBox.getAttribute("imgId") == id2 && !!!textBox2) - textBox2 = textBox; - if (!!textBox1 && !!textBox2) break; + if (textBox.getAttribute("imgId") == id1 && !!!textBox1) textBox1 = textBox; + else if (textBox.getAttribute("imgId") == id2 && !!!textBox2) textBox2 = textBox; + if (!!textBox1 && !!textBox2) break; } - if (!!!insert1 || !!!insert2) return; - if (!!!textBox1 || !!!textBox2) return; - this._swapInserts(insert1,insert2,textBox1,textBox2,remote); + if (!!!insert1 || !!!insert2) return; + if (!!!textBox1 || !!!textBox2) return; + this._swapInserts(insert1, insert2, textBox1, textBox2, remote); } /** @@ -4073,121 +3938,112 @@ class Theatre { * * @params name1 (String) : The label name of the first insert to swap. * @params name2 (String) : The label name of the second insert to swap. - * @params remote (Boolean) : Wither this is being invoked remotely, or locally. + * @params remote (Boolean) : Wither this is being invoked remotely, or locally. */ - swapInsertsByName(name1,name2,remote) { - if (this.portraitDocks.length < 2) return; + swapInsertsByName(name1, name2, remote) { + if (this.portraitDocks.length < 2) return; - let insert1, - insert2, - textBox1, - textBox2; - name1 = name1.toLowerCase(); - name2 = name2.toLowerCase(); + let insert1, insert2, textBox1, textBox2; + name1 = name1.toLowerCase(); + name2 = name2.toLowerCase(); for (let insert of this.portraitDocks) { - if (insert.name == name1 && !!!insert1) - insert1 = insert; - else if (insert.name == name2 && !!!insert2) - insert2 = insert; - if (!!insert1 && !!insert2) break; + if (insert.name == name1 && !!!insert1) insert1 = insert; + else if (insert.name == name2 && !!!insert2) insert2 = insert; + if (!!insert1 && !!insert2) break; } for (let textBox of this._getTextBoxes()) { - if (textBox.getAttribute("name") == name1 && !!!textBox1) - textBox1 = textBox; - else if (textBox.getAttribute("name") == name2 && !!!textBox2) - textBox2 = textBox; - if (!!textBox1 && !!textBox2) break; + if (textBox.getAttribute("name") == name1 && !!!textBox1) textBox1 = textBox; + else if (textBox.getAttribute("name") == name2 && !!!textBox2) textBox2 = textBox; + if (!!textBox1 && !!textBox2) break; } - if (!!!insert1 || !!!insert2) return; - if (!!!textBox1 || !!!textBox2) return; - this._swapInserts(insert1,insert2,textBox1,textBox2,remote); + if (!!!insert1 || !!!insert2) return; + if (!!!textBox1 || !!!textBox2) return; + this._swapInserts(insert1, insert2, textBox1, textBox2, remote); } /** * Swaps Inserts * - * @params insert1 (Object) : The Object representing the first insert to swap. - * @params insert2 (Object) : The Object representing the second insert to swap. + * @params insert1 (Object) : The Object representing the first insert to swap. + * @params insert2 (Object) : The Object representing the second insert to swap. * @params textBox1 (HTMLELement) : The textBox of the first insert to swap. * @params textBox2 (HTMLELement) : The textBox of the second insert to swap. - * @params remote (Boolean) : Wither this is being invoked remotely, or locally. + * @params remote (Boolean) : Wither this is being invoked remotely, or locally. * * @private */ - _swapInserts(insert1,insert2,textBox1,textBox2,remote) { + _swapInserts(insert1, insert2, textBox1, textBox2, remote) { let tsib1n = textBox1.nextSibling, - tsib1p = textBox1.previousSibling, - tsib2n = textBox2.nextSibling, - tsib2p = textBox2.previousSibling; - //console.log("SWAP",textBox1,textBox2); - let adjSwap = false; + tsib1p = textBox1.previousSibling, + tsib2n = textBox2.nextSibling, + tsib2p = textBox2.previousSibling; + //console.log("SWAP",textBox1,textBox2); + let adjSwap = false; // permission check if (!remote && (!this.isPlayerOwned(insert1.imgId) || !this.isPlayerOwned(insert2.imgId))) { ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.CannotSwapControlled")); - return; - } else if (!remote && (!this.isActorOwner(game.user.id,insert1.imgId) && !this.isActorOwner(game.user.id,insert2.imgId))) { + return; + } else if (!remote && !this.isActorOwner(game.user.id, insert1.imgId) && !this.isActorOwner(game.user.id, insert2.imgId)) { ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.CannotSwapOwner")); - return; + return; } - // check the dual dock case if (this._isTextBoxInPrimeBar(textBox1) && this._isTextBoxInSecondBar(textBox2)) { - let primeBar = document.getElementById("theatre-prime-bar"); - let secondBar = document.getElementById("theatre-second-bar"); - insert1.nameOrientation = "right"; - insert1.exitOrientation = "right"; - insert2.nameOrientation = "left"; - insert2.exitOrientation = "left"; - - primeBar.appendChild(textBox2); - secondBar.appendChild(textBox1); + let primeBar = document.getElementById("theatre-prime-bar"); + let secondBar = document.getElementById("theatre-second-bar"); + insert1.nameOrientation = "right"; + insert1.exitOrientation = "right"; + insert2.nameOrientation = "left"; + insert2.exitOrientation = "left"; + + primeBar.appendChild(textBox2); + secondBar.appendChild(textBox1); } else if (this._isTextBoxInPrimeBar(textBox2) && this._isTextBoxInSecondBar(textBox1)) { - let primeBar = document.getElementById("theatre-prime-bar"); - let secondBar = document.getElementById("theatre-second-bar"); - insert1.nameOrientation = "left"; - insert1.exitOrientation = "left"; - insert2.nameOrientation = "right"; - insert2.exitOrientation = "right"; - - primeBar.appendChild(textBox1); - secondBar.appendChild(textBox2); + let primeBar = document.getElementById("theatre-prime-bar"); + let secondBar = document.getElementById("theatre-second-bar"); + insert1.nameOrientation = "left"; + insert1.exitOrientation = "left"; + insert2.nameOrientation = "right"; + insert2.exitOrientation = "right"; + + primeBar.appendChild(textBox1); + secondBar.appendChild(textBox2); } else { // full bar case - if (tsib1n) KHelpers.insertBefore(textBox2,tsib1n); - else if (tsib1p && (tsib1p != textBox2)) KHelpers.insertAfter(textBox2,tsib1p); + if (tsib1n) KHelpers.insertBefore(textBox2, tsib1n); + else if (tsib1p && tsib1p != textBox2) KHelpers.insertAfter(textBox2, tsib1p); else { if (Theatre.DEBUG) console.log("NO TSIB1 and PRIOR"); - KHelpers.insertAfter(textBox2,textBox1); - adjSwap = true; + KHelpers.insertAfter(textBox2, textBox1); + adjSwap = true; } if (!adjSwap) { - if (tsib2n) KHelpers.insertBefore(textBox1,tsib2n); - else if (tsib2p && (tsib2p != textBox1)) KHelpers.insertAfter(textBox1,tsib2p); + if (tsib2n) KHelpers.insertBefore(textBox1, tsib2n); + else if (tsib2p && tsib2p != textBox1) KHelpers.insertAfter(textBox1, tsib2p); else { - if (Theatre.DEBUG) console.log("NO TSIB2 and PRIOR"); - KHelpers.insertAfter(textBox1,textBox2); + if (Theatre.DEBUG) console.log("NO TSIB2 and PRIOR"); + KHelpers.insertAfter(textBox1, textBox2); } } } - if (this.reorderTOId) - window.clearTimeout(this.reorderTOId); + if (this.reorderTOId) window.clearTimeout(this.reorderTOId); - this.reorderTOId = window.setTimeout(()=>{ - Theatre.reorderInserts(); - this.reorderTOId = null; - },250); + this.reorderTOId = window.setTimeout(() => { + Theatre.reorderInserts(); + this.reorderTOId = null; + }, 250); // Push to socket our event if (!remote) { - Theatre.instance._sendSceneEvent("swap",{ - insertid1 : insert1.imgId, - insertid2 : insert2.imgId, - }); + Theatre.instance._sendSceneEvent("swap", { + insertid1: insert1.imgId, + insertid2: insert2.imgId, + }); } } @@ -4196,148 +4052,135 @@ class Theatre { * * @params id1 (String) : The theatreId of the destination insert to move to. * @params id2 (String) : The theatreId of insert to move. - * @params remote (Boolean) : Wither this is being invoked remotely, or locally. + * @params remote (Boolean) : Wither this is being invoked remotely, or locally. */ - moveInsertById(id1,id2,remote) { - if (this.portraitDocks.length < 2) return; + moveInsertById(id1, id2, remote) { + if (this.portraitDocks.length < 2) return; - let insert1, - insert2, - textBox1, - textBox2; + let insert1, insert2, textBox1, textBox2; for (let insert of this.portraitDocks) { - if (insert.imgId == id1 && !!!insert1) - insert1 = insert; - else if (insert.imgId == id2 && !!!insert2) - insert2 = insert; - if (!!insert1 && !!insert2) break; + if (insert.imgId == id1 && !!!insert1) insert1 = insert; + else if (insert.imgId == id2 && !!!insert2) insert2 = insert; + if (!!insert1 && !!insert2) break; } for (let textBox of this._getTextBoxes()) { - if (textBox.getAttribute("imgId") == id1 && !!!textBox1) - textBox1 = textBox; - else if (textBox.getAttribute("imgId") == id2 && !!!textBox2) - textBox2 = textBox; - if (!!textBox1 && !!textBox2) break; + if (textBox.getAttribute("imgId") == id1 && !!!textBox1) textBox1 = textBox; + else if (textBox.getAttribute("imgId") == id2 && !!!textBox2) textBox2 = textBox; + if (!!textBox1 && !!textBox2) break; } - if (!!!insert1 || !!!insert2) return; - if (!!!textBox1 || !!!textBox2) return; - this._moveInsert(insert1,insert2,textBox1,textBox2,remote); + if (!!!insert1 || !!!insert2) return; + if (!!!textBox1 || !!!textBox2) return; + this._moveInsert(insert1, insert2, textBox1, textBox2, remote); } /** * Move an insert * - * @params insert1 (Object) : The Object representing the destination insert. + * @params insert1 (Object) : The Object representing the destination insert. * @params insert2 (Object) : The Object representing insert to move * * @params textBox1 (HTMLELement) : The textBox of the destination textbox * @params textBox2 (HTMLELement) : The textBox of the textbox to move * - * @params remote (Boolean) : Wither this is being invoked remotely, or locally. + * @params remote (Boolean) : Wither this is being invoked remotely, or locally. * * @private */ - _moveInsert(insert1,insert2,textBox1,textBox2,remote) { + _moveInsert(insert1, insert2, textBox1, textBox2, remote) { let tsib1n = textBox1.nextSibling, - tsib1p = textBox1.previousSibling, - tsib2n = textBox2.nextSibling, - tsib2p = textBox2.previousSibling; - //console.log("SWAP",textBox1,textBox2); - let adjSwap = false; + tsib1p = textBox1.previousSibling, + tsib2n = textBox2.nextSibling, + tsib2p = textBox2.previousSibling; + //console.log("SWAP",textBox1,textBox2); + let adjSwap = false; // permission check - if (!remote && !this.isActorOwner(game.user.id,insert2.imgId)) { + if (!remote && !this.isActorOwner(game.user.id, insert2.imgId)) { ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.CannotMoveOwner")); - return; + return; } else if (!remote && (!this.isPlayerOwned(insert1.imgId) || !this.isPlayerOwned(insert2.imgId))) { ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.CannotMoveControlled")); - return; - } + return; + } // check the dual dock case if (this._isTextBoxInPrimeBar(textBox1) && this._isTextBoxInSecondBar(textBox2)) { - let primeBar = document.getElementById("theatre-prime-bar"); - let secondBar = document.getElementById("theatre-second-bar"); - insert1.nameOrientation = "right"; - insert1.exitOrientation = "right"; - insert2.nameOrientation = "left"; - insert2.exitOrientation = "left"; - - primeBar.appendChild(textBox2); - secondBar.appendChild(textBox1); + let primeBar = document.getElementById("theatre-prime-bar"); + let secondBar = document.getElementById("theatre-second-bar"); + insert1.nameOrientation = "right"; + insert1.exitOrientation = "right"; + insert2.nameOrientation = "left"; + insert2.exitOrientation = "left"; + + primeBar.appendChild(textBox2); + secondBar.appendChild(textBox1); } else if (this._isTextBoxInPrimeBar(textBox2) && this._isTextBoxInSecondBar(textBox1)) { - let primeBar = document.getElementById("theatre-prime-bar"); - let secondBar = document.getElementById("theatre-second-bar"); - insert1.nameOrientation = "left"; - insert1.exitOrientation = "left"; - insert2.nameOrientation = "right"; - insert2.exitOrientation = "right"; - - primeBar.appendChild(textBox1); - secondBar.appendChild(textBox2); + let primeBar = document.getElementById("theatre-prime-bar"); + let secondBar = document.getElementById("theatre-second-bar"); + insert1.nameOrientation = "left"; + insert1.exitOrientation = "left"; + insert2.nameOrientation = "right"; + insert2.exitOrientation = "right"; + + primeBar.appendChild(textBox1); + secondBar.appendChild(textBox2); } else { // full bar case - if (insert2.order > insert1.order) - KHelpers.insertBefore(textBox2,textBox1); - else - KHelpers.insertAfter(textBox2,textBox1); + if (insert2.order > insert1.order) KHelpers.insertBefore(textBox2, textBox1); + else KHelpers.insertAfter(textBox2, textBox1); } - if (this.reorderTOId) - window.clearTimeout(this.reorderTOId); + if (this.reorderTOId) window.clearTimeout(this.reorderTOId); - this.reorderTOId = window.setTimeout(()=>{ - Theatre.reorderInserts(); - this.reorderTOId = null; - },250); + this.reorderTOId = window.setTimeout(() => { + Theatre.reorderInserts(); + this.reorderTOId = null; + }, 250); // Push to socket our event if (!remote) { - Theatre.instance._sendSceneEvent("move",{ - insertid1 : insert1.imgId, - insertid2 : insert2.imgId, - }); + Theatre.instance._sendSceneEvent("move", { + insertid1: insert1.imgId, + insertid2: insert2.imgId, + }); } } - /** * Is the textbox in the prime bar * - * @params textBox (HTMLElement) : The textBox to check. + * @params textBox (HTMLElement) : The textBox to check. * - * @return (Boolean) True if the textBox is in the Prime Bar, false otherwise. + * @return (Boolean) True if the textBox is in the Prime Bar, false otherwise. * * @private */ _isTextBoxInPrimeBar(textBox) { - let primeBar = document.getElementById("theatre-prime-bar"); - let id = textBox.getAttribute("imgId"); + let primeBar = document.getElementById("theatre-prime-bar"); + let id = textBox.getAttribute("imgId"); for (let btb of primeBar.children) { - if (btb.getAttribute("imgId") == id) - return true; + if (btb.getAttribute("imgId") == id) return true; } - return false; + return false; } /** * Is the textbox in the second bar * - * @params textBox (HTMLElement) : The textBox to check. + * @params textBox (HTMLElement) : The textBox to check. * - * @return (Boolean) True if the textBox is in the Second Bar, false otherwise. + * @return (Boolean) True if the textBox is in the Second Bar, false otherwise. * * @private */ _isTextBoxInSecondBar(textBox) { - let secondBar = document.getElementById("theatre-second-bar"); - let id = textBox.getAttribute("imgId"); + let secondBar = document.getElementById("theatre-second-bar"); + let id = textBox.getAttribute("imgId"); for (let btb of secondBar.children) { - if (btb.getAttribute("imgId") == id) - return true; + if (btb.getAttribute("imgId") == id) return true; } - return false; + return false; } /** @@ -4345,28 +4188,28 @@ class Theatre { * * @params id (String) : The theatreId of the insert to push. * @params isLeft (Boolean) : Wither we're pushing left or right. - * @params remote (Boolean) : Wither this is being invoked remotely, or locally. + * @params remote (Boolean) : Wither this is being invoked remotely, or locally. */ pushInsertById(id, isLeft, remote) { - if (this.portraitDocks.length <= 2) return; + if (this.portraitDocks.length <= 2) return; - let targInsert; - let targTextBox; + let targInsert; + let targTextBox; for (let insert of this.portraitDocks) { if (insert.imgId == id) { - targInsert = insert; - break; + targInsert = insert; + break; } } for (let textBox of this._getTextBoxes()) { if (textBox.getAttribute("imgId") == id) { - targTextBox = textBox; - break; + targTextBox = textBox; + break; } } - if (!!!targInsert || !!!targTextBox) return; + if (!!!targInsert || !!!targTextBox) return; - this._pushInsert(targInsert,targTextBox,isLeft, remote); + this._pushInsert(targInsert, targTextBox, isLeft, remote); } /** @@ -4374,65 +4217,63 @@ class Theatre { * * @params name (String) : The label name of the insert to push. * @params isLeft (Boolean) : Wither we're pushing left or right. - * @params remote (Boolean) : Wither this is being invoked remotely, or locally. + * @params remote (Boolean) : Wither this is being invoked remotely, or locally. */ pushInsertByName(name, isLeft, remote) { - if (this.portraitDocks.length <= 2) return; + if (this.portraitDocks.length <= 2) return; - let targInsert; - let targTextBox; + let targInsert; + let targTextBox; for (let insert of this.portraitDocks) { if (insert.name == name) { - targInsert = insert; - break; + targInsert = insert; + break; } } for (let textBox of this._getTextBoxes()) { if (textBox.getAttribute("name") == name) { - targTextBox = textBox; - break; + targTextBox = textBox; + break; } } - if (!!!targInsert || !!!targTextBox) return; + if (!!!targInsert || !!!targTextBox) return; - this._pushInsert(targInsert,targTextBox,isLeft, remote); + this._pushInsert(targInsert, targTextBox, isLeft, remote); } /** * Push Insert left or right of all others * - * @params insert (Object) : The Object represeting the insert. - * @params textBox (HTMLElement) : The textBox of the insert. - * @params isLeft (Boolean) : Wither we're pushing left or right. - * @params remote (Boolean) : Wither this is being invoked remotely, or locally. + * @params insert (Object) : The Object represeting the insert. + * @params textBox (HTMLElement) : The textBox of the insert. + * @params isLeft (Boolean) : Wither we're pushing left or right. + * @params remote (Boolean) : Wither this is being invoked remotely, or locally. * * @private */ - _pushInsert(insert,textBox,isLeft, remote) { - let textBoxes = this._getTextBoxes(); - let firstInsert = this.portraitDocks[0]; - let lastInsert = this.portraitDocks[this.portraitDocks.length-1]; - let firstTextBox = textBoxes[0] ; - let lastTextBox = textBoxes[textBoxes.length-1]; + _pushInsert(insert, textBox, isLeft, remote) { + let textBoxes = this._getTextBoxes(); + let firstInsert = this.portraitDocks[0]; + let lastInsert = this.portraitDocks[this.portraitDocks.length - 1]; + let firstTextBox = textBoxes[0]; + let lastTextBox = textBoxes[textBoxes.length - 1]; - if (!!!firstInsert || !!!lastInsert || !!!firstTextBox || !!!lastTextBox) return; + if (!!!firstInsert || !!!lastInsert || !!!firstTextBox || !!!lastTextBox) return; // permission check - if (!remote && !this.isActorOwner(game.user.id,insert.imgId)) { + if (!remote && !this.isActorOwner(game.user.id, insert.imgId)) { ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.DoNotControl")); - return; + return; } else if (!remote && (isLeft ? !this.isPlayerOwned(firstInsert.imgId) : !this.isPlayerOwned(lastInsert.imgId))) { - if (isLeft) - ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.CannotPushFront")); - else - ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.CannotPushBack")); - return; + if (isLeft) ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.CannotPushFront")); + else ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.CannotPushBack")); + return; } if (isLeft) { - KHelpers.insertBefore(textBox,firstTextBox); + KHelpers.insertBefore(textBox, firstTextBox); } else { - KHelpers.insertAfter(textBox,lastTextBox); + KHelpers.insertAfter(textBox, lastTextBox); } /* @@ -4444,181 +4285,179 @@ class Theatre { this.reorderTOId = null; },500); */ - Theatre.reorderInserts(); + Theatre.reorderInserts(); // Push to socket our event if (!remote) { - Theatre.instance._sendSceneEvent("push",{ - insertid : insert.imgId, - tofront : isLeft - }); + Theatre.instance._sendSceneEvent("push", { + insertid: insert.imgId, + tofront: isLeft, + }); } } /** * Mirror a portrait by ID * - * @params id (String) : The theatreId of the insert we wish to mirror. - * @params remote (Boolean) : Wither this is being invoked remotely, or locally. + * @params id (String) : The theatreId of the insert we wish to mirror. + * @params remote (Boolean) : Wither this is being invoked remotely, or locally. */ - mirrorInsertById(id,remote) { - let insert = this.getInsertById(id); - if (!insert) return; + mirrorInsertById(id, remote) { + let insert = this.getInsertById(id); + if (!insert) return; - this._mirrorInsert(insert,remote); + this._mirrorInsert(insert, remote); } /** * Mirror a portrait by Name * - * @params name (String) : The label name of the insert we wish to mirror. - * @params remote (Boolean) : Wither this is being invoked remotely, or locally. + * @params name (String) : The label name of the insert we wish to mirror. + * @params remote (Boolean) : Wither this is being invoked remotely, or locally. */ - mirrorInsertByName(name,remote) { - let insert = this.getInsertByName(name); - if (!insert) return; + mirrorInsertByName(name, remote) { + let insert = this.getInsertByName(name); + if (!insert) return; - this._mirrorInsert(insert,remote); + this._mirrorInsert(insert, remote); } /** * Is an insertMirrored give Id * - * @params id (String) : The theatreId of the insert we wish to mirror. + * @params id (String) : The theatreId of the insert we wish to mirror. * return (Boolean) : True if the insert is mirrored, false otherwise. */ isInsertMirrored(id) { - let insert = this.getInsertByName(id); - return insert.mirrored; + let insert = this.getInsertByName(id); + return insert.mirrored; } /** * Mirror a portrait * * @params insert (Object) : The Object represeting the insert. - * @params remote (Boolean) : Wither this is being invoked remotely, or locally. + * @params remote (Boolean) : Wither this is being invoked remotely, or locally. * * @private */ - _mirrorInsert(insert,remote) { + _mirrorInsert(insert, remote) { // permission check - if (!remote && (!this.isActorOwner(game.user.id,insert.imgId))) { + if (!remote && !this.isActorOwner(game.user.id, insert.imgId)) { ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.DoNotControl")); - return; + return; } let tweenId = "mirrorFlip"; - let broadcast = false; + let broadcast = false; if (!insert.mirrored && !insert.tweens[tweenId]) { - insert.mirrored = true; - let tween = TweenMax.to(insert.portraitContainer,0.5,{ - pixi:{scaleX: -1}, + insert.mirrored = true; + let tween = TweenMax.to(insert.portraitContainer, 0.5, { + pixi: { scaleX: -1 }, ease: Power4.easeInOut, - onComplete: function(ctx,imgId,tweenId) { + onComplete: function (ctx, imgId, tweenId) { // decrement the rendering accumulator - ctx._removeDockTween(imgId,this,tweenId); + ctx._removeDockTween(imgId, this, tweenId); }, - onCompleteParams: [this,insert.imgId,tweenId], - }); - this._addDockTween(insert.imgId,tween,tweenId); - broadcast = true; + onCompleteParams: [this, insert.imgId, tweenId], + }); + this._addDockTween(insert.imgId, tween, tweenId); + broadcast = true; } else if (!insert.tweens[tweenId]) { - insert.mirrored = false; - let tween = TweenMax.to(insert.portraitContainer,0.5,{ - pixi:{scaleX: 1}, + insert.mirrored = false; + let tween = TweenMax.to(insert.portraitContainer, 0.5, { + pixi: { scaleX: 1 }, ease: Power4.easeInOut, - onComplete: function(ctx,imgId,tweenId) { + onComplete: function (ctx, imgId, tweenId) { // decrement the rendering accumulator - ctx._removeDockTween(imgId,this,tweenId); + ctx._removeDockTween(imgId, this, tweenId); }, - onCompleteParams: [this,insert.imgId,tweenId], - }); - this._addDockTween(insert.imgId,tween,tweenId); - broadcast = true; + onCompleteParams: [this, insert.imgId, tweenId], + }); + this._addDockTween(insert.imgId, tween, tweenId); + broadcast = true; } // Push to socket our event if (!remote && broadcast) { - Theatre.instance._sendSceneEvent("positionupdate",{ - insertid : insert.imgId, + Theatre.instance._sendSceneEvent("positionupdate", { + insertid: insert.imgId, position: { x: insert.portraitContainer.x, y: insert.portraitContainer.y, - mirror: insert.mirrored - } - }); + mirror: insert.mirrored, + }, + }); } - } /** * Reset an insert's postion/mirror state by Id * * @param id (String) : The theatreId of the insert to reset. - * @params remote (Boolean) : Wither this is being invoked remotely, or locally. + * @params remote (Boolean) : Wither this is being invoked remotely, or locally. */ - resetInsertById(id,remote) { - let insert = this.getInsertById(id); + resetInsertById(id, remote) { + let insert = this.getInsertById(id); - this._resetPortraitPosition(insert, remote); + this._resetPortraitPosition(insert, remote); } /** * Reset an insert's postion/mirror state by Id * * @param name (String) : The name label of the insert to reset. - * @params remote (Boolean) : Wither this is being invoked remotely, or locally. + * @params remote (Boolean) : Wither this is being invoked remotely, or locally. */ - resetInsertByName(name,remote) { - let insert = this.getInsertByName(name); + resetInsertByName(name, remote) { + let insert = this.getInsertByName(name); - this._resetPortraitPosition(insert, remote); + this._resetPortraitPosition(insert, remote); } /** * Resets a portrait position/morror state * * @params insert (Object) : The Object represeting an insert. - * @params remote (Boolean) : Wither this is being invoked remotely, or locally. + * @params remote (Boolean) : Wither this is being invoked remotely, or locally. * * @private */ _resetPortraitPosition(insert, remote) { // permission check - if (!remote && !this.isActorOwner(game.user.id,insert.imgId)) { + if (!remote && !this.isActorOwner(game.user.id, insert.imgId)) { ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.DoNotControl")); - return; + return; } - let tweenId,tween; + let tweenId, tween; // reset mirroring // reset position of portraitContainer - insert.mirrored = false; - tweenId = "portraitMove"; - tween = TweenMax.to(insert.portraitContainer,0.5,{ - pixi:{scaleX: 1, x: insert.portrait.width/2, y: insert.portrait.height/2}, + insert.mirrored = false; + tweenId = "portraitMove"; + tween = TweenMax.to(insert.portraitContainer, 0.5, { + pixi: { scaleX: 1, x: insert.portrait.width / 2, y: insert.portrait.height / 2 }, ease: Power3.easeOut, - onComplete: function(ctx,imgId,tweenId) { + onComplete: function (ctx, imgId, tweenId) { // decrement the rendering accumulator - if (Theatre.DEBUG) console.log("portrait move onComplete %s",tweenId); - ctx._removeDockTween(imgId,this,tweenId); + if (Theatre.DEBUG) console.log("portrait move onComplete %s", tweenId); + ctx._removeDockTween(imgId, this, tweenId); }, - onCompleteParams: [this,insert.imgId,tweenId] - }); - this._addDockTween(insert.imgId,tween,tweenId); + onCompleteParams: [this, insert.imgId, tweenId], + }); + this._addDockTween(insert.imgId, tween, tweenId); // Push to socket our event if (!remote) { - Theatre.instance._sendSceneEvent("positionupdate",{ - insertid : insert.imgId, - position: {x: insert.portrait.width/2, y: insert.portrait.height/2 ,mirror: false} - }); + Theatre.instance._sendSceneEvent("positionupdate", { + insertid: insert.imgId, + position: { x: insert.portrait.width / 2, y: insert.portrait.height / 2, mirror: false }, + }); } - } /** * first verify, then immediately execute the set of tweens - * defined in the animation syntax. + * defined in the animation syntax. * * If any tweens in the syntax are incorrect, none are executed, and * an empty array is returned indicating no tweens were performed @@ -4628,91 +4467,84 @@ class Theatre { * @params animName (String) : The animation name. * @params animSyntax (String) : The animation syntax. * @params resMap (Array[Object]) : The resource map to use consisting of - * {name: (String), path: (String)} tuples. + * {name: (String), path: (String)} tuples. * @params insert (Object) : The object represeting the insert that will contain this - * animation. + * animation. */ - addTweensFromAnimationSyntax(animName,animSyntax,resMap,insert) { - let tweenParams = Theatre.verifyAnimationSyntax(animSyntax); + addTweensFromAnimationSyntax(animName, animSyntax, resMap, insert) { + let tweenParams = Theatre.verifyAnimationSyntax(animSyntax); - let resTarget = resMap.find(e => (e.name == tweenParams[0].resName)); - let resource = PIXI.Loader.shared.resources[resTarget.path]; + let resTarget = resMap.find((e) => e.name == tweenParams[0].resName); + let resource = PIXI.Loader.shared.resources[resTarget.path]; - if (Theatre.DEBUG) console.log("Adding tweens for animation '%s' from syntax: %s with params: ", animName, animSyntax, tweenParams); - //console.log("Resource path is %s, resource: ", resTarget.path, resource); + if (Theatre.DEBUG) console.log("Adding tweens for animation '%s' from syntax: %s with params: ", animName, animSyntax, tweenParams); + //console.log("Resource path is %s, resource: ", resTarget.path, resource); if (!resource) { - console.log ('ERROR: resource name : "%s" with path "%s" does not exist!',tweenParams[idx].resName,resTarget.path); - return; + console.log('ERROR: resource name : "%s" with path "%s" does not exist!', tweenParams[idx].resName, resTarget.path); + return; } - let sprite = new PIXI.Sprite(resource.texture); - let spriteWidth = resource.texture.width; - let spriteHeight = resource.texture.height; - sprite.anchor.set(0.5); - insert.portraitContainer.addChild(sprite); - - for (let idx=0; idx e == prop.name)) { - prop.initial = Number(prop.initial.match(/-*\d+\.*\d*/)[0] || 0); - prop.final = Number(prop.final.match(/-*\d+\.*\d*/)[0] || 0); + prop.initial = (Number(prop.initial.match(/-*\d+\.*\d*/)[0] || 0) / 100) * (prop.name == "x" ? insert.portrait.width : insert.portrait.height); + prop.final = (Number(prop.final.match(/-*\d+\.*\d*/)[0] || 0) / 100) * (prop.name == "x" ? insert.portrait.width : insert.portrait.height); + } else if (["scaleX", "scaleY", "rotation"].some((e) => e == prop.name)) { + prop.initial = Number(prop.initial.match(/-*\d+\.*\d*/)[0] || 0); + prop.final = Number(prop.final.match(/-*\d+\.*\d*/)[0] || 0); } - if (Theatre.DEBUG) console.log("new %s : %s,%s : w:%s,h:%s",prop.name,prop.initial,prop.final,insert.portrait.width,insert.portrait.height); + if (Theatre.DEBUG) console.log("new %s : %s,%s : w:%s,h:%s", prop.name, prop.initial, prop.final, insert.portrait.width, insert.portrait.height); } // special case for some GSAP -> PIXI names switch (prop.name) { case "scaleX": - sprite.scale.x = prop.initial; - break; + sprite.scale.x = prop.initial; + break; case "scaleY": - sprite.scale.y = prop.initial; - break; + sprite.scale.y = prop.initial; + break; case "rotation": - sprite.rotation = prop.initial * (Math.PI/180); - break; + sprite.rotation = prop.initial * (Math.PI / 180); + break; default: - sprite[prop.name] = prop.initial; - break; + sprite[prop.name] = prop.initial; + break; } - pixiParams[prop.name] = prop.final; + pixiParams[prop.name] = prop.final; } - let tweenId = animName+idx; - let tween = TweenMax.to(sprite,tweenParams[idx].duration,{ + let tweenId = animName + idx; + let tween = TweenMax.to(sprite, tweenParams[idx].duration, { pixi: pixiParams, ease: ease, delay: delay, @@ -4723,18 +4555,16 @@ class Theatre { /*onRepeat: function() { console.log("ANIMATION tween is repeating!",this); }, */ - onComplete: function(ctx,imgId,tweenId) { - if (Theatre.DEBUG) console.log("ANIMATION tween complete!"); + onComplete: function (ctx, imgId, tweenId) { + if (Theatre.DEBUG) console.log("ANIMATION tween complete!"); // decrement the rendering accumulator - ctx._removeDockTween(imgId,this,tweenId); + ctx._removeDockTween(imgId, this, tweenId); // remove our own reference from the dockContainer tweens }, - onCompleteParams: [this,insert.imgId,tweenId] - }); - if (repeat != 0) - tween.duration(tweenParams[idx].duration); - this._addDockTween(insert.imgId,tween,tweenId); - + onCompleteParams: [this, insert.imgId, tweenId], + }); + if (repeat != 0) tween.duration(tweenParams[idx].duration); + this._addDockTween(insert.imgId, tween, tweenId); } } @@ -4749,199 +4579,199 @@ class Theatre { * * @params params (Object) : The set of emotion properties. * @params userDefault (Boolean) : Wither to use the default user settings over the - * settings in the params object. + * settings in the params object. * - * @return (Object) : The object containing the emotion properties to be used. + * @return (Object) : The object containing the emotion properties to be used. * * @private */ - _getInitialEmotionSetFromInsertParams(params,useDefault) { - if (Theatre.DEBUG) console.log("use default? %s", !useDefault); + _getInitialEmotionSetFromInsertParams(params, useDefault) { + if (Theatre.DEBUG) console.log("use default? %s", !useDefault); let emotions = { - emote : (!useDefault && params.settings.emote ? params.settings.emote : null) - || (this.userEmotes[game.user.id] ? this.userEmotes[game.user.id].emote : null), - textFlyin : (!useDefault && params.settings.emote && params.emotes[params.settings.emote] && params.emotes[params.settings.emote].settings - ? params.emotes[params.settings.emote].settings.textflyin : null) - || (!useDefault ? params.settings.textflyin : null) - || (this.userEmotes[game.user.id] ? this.userEmotes[game.user.id].textFlyin : null), - textStanding : (!useDefault && params.settings.emote && params.emotes[params.settings.emote] && params.emotes[params.settings.emote].settings - ? params.emote.settings.textstanding : null) - || (!useDefault ? params.settings.textstanding : null) - || (this.userEmotes[game.user.id] ? this.userEmotes[game.user.id].textStanding : null), - textFont : (!useDefault && params.settings.emote && params.emotes[params.settings.emote] && params.emotes[params.settings.emote].settings - ? params.emote.settings.textfont : null) - || (!useDefault ? params.settings.textfont : null) - || (this.userEmotes[game.user.id] ? this.userEmotes[game.user.id].textFont : null), - textSize : (!useDefault && params.settings.emote && params.emotes[params.settings.emote] && params.emotes[params.settings.emote].settings - ? params.emote.settings.textsize : null) - || (!useDefault ? params.settings.textsize : null) - || (this.userEmotes[game.user.id] ? this.userEmotes[game.user.id].textSize : null), - textColor : (!useDefault && params.settings.emote && params.emotes[params.settings.emote] && params.emotes[params.settings.emote].settings - ? params.emote.settings.textcolor : null) - || (!useDefault ? params.settings.textcolor : null) - || (this.userEmotes[game.user.id] ? this.userEmotes[game.user.id].textColor : null) - } - return emotions; + emote: (!useDefault && params.settings.emote ? params.settings.emote : null) || (this.userEmotes[game.user.id] ? this.userEmotes[game.user.id].emote : null), + textFlyin: + (!useDefault && params.settings.emote && params.emotes[params.settings.emote] && params.emotes[params.settings.emote].settings + ? params.emotes[params.settings.emote].settings.textflyin + : null) || + (!useDefault ? params.settings.textflyin : null) || + (this.userEmotes[game.user.id] ? this.userEmotes[game.user.id].textFlyin : null), + textStanding: + (!useDefault && params.settings.emote && params.emotes[params.settings.emote] && params.emotes[params.settings.emote].settings + ? params.emote.settings.textstanding + : null) || + (!useDefault ? params.settings.textstanding : null) || + (this.userEmotes[game.user.id] ? this.userEmotes[game.user.id].textStanding : null), + textFont: + (!useDefault && params.settings.emote && params.emotes[params.settings.emote] && params.emotes[params.settings.emote].settings + ? params.emote.settings.textfont + : null) || + (!useDefault ? params.settings.textfont : null) || + (this.userEmotes[game.user.id] ? this.userEmotes[game.user.id].textFont : null), + textSize: + (!useDefault && params.settings.emote && params.emotes[params.settings.emote] && params.emotes[params.settings.emote].settings + ? params.emote.settings.textsize + : null) || + (!useDefault ? params.settings.textsize : null) || + (this.userEmotes[game.user.id] ? this.userEmotes[game.user.id].textSize : null), + textColor: + (!useDefault && params.settings.emote && params.emotes[params.settings.emote] && params.emotes[params.settings.emote].settings + ? params.emote.settings.textcolor + : null) || + (!useDefault ? params.settings.textcolor : null) || + (this.userEmotes[game.user.id] ? this.userEmotes[game.user.id].textColor : null), + }; + return emotions; } /** * Activate an insert by Id, if it is staged to the navbar * * @params id (String) : The theatreId of the insert to activate. - * @params ev (Event) : The event that possibly triggered this activation. + * @params ev (Event) : The event that possibly triggered this activation. */ - activateInsertById(id,ev) { - let actorId = id.replace("theatre-",""); - let navItem = this.getNavItemById(id); + activateInsertById(id, ev) { + let actorId = id.replace("theatre-", ""); + let navItem = this.getNavItemById(id); if (!navItem) { - let actor = game.actors.get(actorId); - Theatre.addToNavBar(actor.data); - navItem = this.getNavItemById(id); + let actor = game.actors.get(actorId); + Theatre.addToNavBar(actor.data); + navItem = this.getNavItemById(id); } - if (!navItem) return; - + if (!navItem) return; - let params = this._getInsertParamsFromActorId(actorId); + let params = this._getInsertParamsFromActorId(actorId); - if (Theatre.DEBUG) console.log(" set as active"); + if (Theatre.DEBUG) console.log(" set as active"); // set as user active // If the insert does not exist in the dock, add it, // If it does, then simply toggle it as active if it isn't already // If it's already active, and we're GM, then we want to transition to 'god mode' // voice, thus we simply un-activate our character, and assume GM voice again // (the default, if no insert selected) - let insert = this.getInsertById(id); - let textBox = this.getTextBoxById(id); - let label = (insert ? insert.label : null); + let insert = this.getInsertById(id); + let textBox = this.getTextBoxById(id); + let label = insert ? insert.label : null; // remove old speaking as, shift it - let oldSpeakingItem = this.getNavItemById(this.speakingAs); - let oldSpeakingInsert = this.getInsertById(this.speakingAs); - let oldSpeakingLabel = (oldSpeakingInsert ? oldSpeakingInsert.label : null); - if (oldSpeakingItem) - KHelpers.removeClass(oldSpeakingItem,"theatre-control-nav-bar-item-speakingas"); + let oldSpeakingItem = this.getNavItemById(this.speakingAs); + let oldSpeakingInsert = this.getInsertById(this.speakingAs); + let oldSpeakingLabel = oldSpeakingInsert ? oldSpeakingInsert.label : null; + if (oldSpeakingItem) KHelpers.removeClass(oldSpeakingItem, "theatre-control-nav-bar-item-speakingas"); if (oldSpeakingInsert) { - this._removeDockTween(this.speakingAs,null,"nameSpeakingPulse"); - oldSpeakingInsert.label.tint = 0xFFFFFF; + this._removeDockTween(this.speakingAs, null, "nameSpeakingPulse"); + oldSpeakingInsert.label.tint = 0xffffff; } // if narrator is active, deactivate it and push the button up - if (game.user.isGM && this.speakingAs == Theatre.NARRATOR) - this.toggleNarratorBar(false); + if (game.user.isGM && this.speakingAs == Theatre.NARRATOR) this.toggleNarratorBar(false); // if this insert / textbox pair is being removed, stop - if (!!insert && textBox.getAttribute("deleting")) - return; - + if (!!insert && textBox.getAttribute("deleting")) return; + if (!!insert) { // already in theatre // if not same id toggle it - let cimg = this.getTheatreCoverPortrait(); + let cimg = this.getTheatreCoverPortrait(); if (this.speakingAs != id) { - this.speakingAs = id; - KHelpers.addClass(navItem,"theatre-control-nav-bar-item-speakingas"); - TweenMax.to(Theatre.instance.theatreNavBar,.4, {scrollTo:{x:navItem.offsetLeft,offsetX:Theatre.instance.theatreNavBar.offsetWidth/2}}) + this.speakingAs = id; + KHelpers.addClass(navItem, "theatre-control-nav-bar-item-speakingas"); + TweenMax.to(Theatre.instance.theatreNavBar, 0.4, { scrollTo: { x: navItem.offsetLeft, offsetX: Theatre.instance.theatreNavBar.offsetWidth / 2 } }); // add label pulse - insert.label.tint = 0xFFFFFF; - let tweenId = "nameSpeakingPulse"; - let tween = TweenMax.to(insert.label,1,{ - pixi:{tint: 0xFF6400}, + insert.label.tint = 0xffffff; + let tweenId = "nameSpeakingPulse"; + let tween = TweenMax.to(insert.label, 1, { + pixi: { tint: 0xff6400 }, ease: Power0.easeNone, repeat: -1, yoyo: true, - onComplete: function(ctx,imgId,tweenId) { + onComplete: function (ctx, imgId, tweenId) { // decrement the rendering accumulator - ctx._removeDockTween(imgId,this,tweenId); + ctx._removeDockTween(imgId, this, tweenId); // remove our own reference from the dockContainer tweens }, - onCompleteParams: [this,id,tweenId] - }); - this._addDockTween(id,tween,tweenId); + onCompleteParams: [this, id, tweenId], + }); + this._addDockTween(id, tween, tweenId); // change cover - cimg.setAttribute("src",params.src); + cimg.setAttribute("src", params.src); //cimg.style.left = `calc(100% - ${this.theatreChatCover.offsetHeight}px)` - cimg.style.width = `${this.theatreChatCover.offsetHeight}px` - cimg.style.opacity = "0.3"; + cimg.style.width = `${this.theatreChatCover.offsetHeight}px`; + cimg.style.opacity = "0.3"; // push focus to chat-message - let chatMessage = document.getElementById("chat-message"); - chatMessage.focus(); + let chatMessage = document.getElementById("chat-message"); + chatMessage.focus(); // send typing event - //this._sendTypingEvent(); - //this.setUserTyping(game.user.id,this.speakingAs); + //this._sendTypingEvent(); + //this.setUserTyping(game.user.id,this.speakingAs); } else { - this.speakingAs = null; + this.speakingAs = null; // clear cover - cimg.removeAttribute("src"); - cimg.style.opacity = "0"; + cimg.removeAttribute("src"); + cimg.style.opacity = "0"; // clear typing theatreId data - this.removeUserTyping(game.user.id); - this.usersTyping[game.user.id].theatreId = null; + this.removeUserTyping(game.user.id); + this.usersTyping[game.user.id].theatreId = null; } } else { - let src = params.src; - let name = params.name; - let optAlign = params.optalign; - let cimg = this.getTheatreCoverPortrait(); - let emotions; + let src = params.src; + let name = params.name; + let optAlign = params.optalign; + let cimg = this.getTheatreCoverPortrait(); + let emotions; // determine if to launch with actor saves or default settings - if (ev && ev.altKey) - emotions = Theatre.instance._getInitialEmotionSetFromInsertParams(params,true); - else - emotions = Theatre.instance._getInitialEmotionSetFromInsertParams(params); + if (ev && ev.altKey) emotions = Theatre.instance._getInitialEmotionSetFromInsertParams(params, true); + else emotions = Theatre.instance._getInitialEmotionSetFromInsertParams(params); - if (Theatre.DEBUG) console.log("ACTIVATING AND INJECTING with Emotions: ",emotions); + if (Theatre.DEBUG) console.log("ACTIVATING AND INJECTING with Emotions: ", emotions); if (ev && !ev.shiftKey) { - if (game.user.isGM) - this.injectLeftPortrait(src,name,id,optAlign,emotions); - else - this.injectRightPortrait(src,name,id,optAlign,emotions); - } else - this.injectRightPortrait(src,name,id,optAlign,emotions); - - this.speakingAs = id; - KHelpers.addClass(navItem,"theatre-control-nav-bar-item-speakingas"); - TweenMax.to(Theatre.instance.theatreNavBar,.4,{scrollTo:{x:navItem.offsetLeft,offsetX:Theatre.instance.theatreNavBar.offsetWidth/2}}) - - window.setTimeout(()=>{ - insert = this.getInsertById(id); + if (game.user.isGM) this.injectLeftPortrait(src, name, id, optAlign, emotions); + else this.injectRightPortrait(src, name, id, optAlign, emotions); + } else this.injectRightPortrait(src, name, id, optAlign, emotions); + + this.speakingAs = id; + KHelpers.addClass(navItem, "theatre-control-nav-bar-item-speakingas"); + TweenMax.to(Theatre.instance.theatreNavBar, 0.4, { scrollTo: { x: navItem.offsetLeft, offsetX: Theatre.instance.theatreNavBar.offsetWidth / 2 } }); + + window.setTimeout(() => { + insert = this.getInsertById(id); // if our insert hasn't been destroyed if (insert && !!insert.dockContainer && this.speakingAs == id) { - label = this.label; + label = this.label; // add label pulse - insert.label.tint = 0xFFFFFF; - let tweenId = "nameSpeakingPulse"; - let tween = TweenMax.to(insert.label,1,{ - pixi:{tint: 0xFF6400}, + insert.label.tint = 0xffffff; + let tweenId = "nameSpeakingPulse"; + let tween = TweenMax.to(insert.label, 1, { + pixi: { tint: 0xff6400 }, ease: Power0.easeNone, repeat: -1, yoyo: true, - onComplete: function(ctx,imgId,tweenId) { + onComplete: function (ctx, imgId, tweenId) { // decrement the rendering accumulator - ctx._removeDockTween(imgId,this,tweenId); + ctx._removeDockTween(imgId, this, tweenId); // remove our own reference from the dockContainer tweens }, - onCompleteParams: [this,id,tweenId] - }); - this._addDockTween(id,tween,tweenId); + onCompleteParams: [this, id, tweenId], + }); + this._addDockTween(id, tween, tweenId); } - },1000); + }, 1000); // change cover - cimg.setAttribute("src",src); + cimg.setAttribute("src", src); //cimg.style.left = `calc(100% - ${this.theatreChatCover.offsetHeight}px)` - cimg.style.width = `${this.theatreChatCover.offsetHeight}px` - cimg.style.opacity = "0.3"; + cimg.style.width = `${this.theatreChatCover.offsetHeight}px`; + cimg.style.opacity = "0.3"; // push focus to chat-message - let chatMessage = document.getElementById("chat-message"); - chatMessage.focus(); + let chatMessage = document.getElementById("chat-message"); + chatMessage.focus(); } // send typing event - this._sendTypingEvent(); - this.setUserTyping(game.user.id,this.speakingAs); + this._sendTypingEvent(); + this.setUserTyping(game.user.id, this.speakingAs); // re-render the emote menu (expensive) - this.renderEmoteMenu(); + this.renderEmoteMenu(); } /** @@ -4949,243 +4779,245 @@ class Theatre { * fading it away * * @params theatreId (String) : The theatreId of the textBox we want to decay. - * @params remote (Boolean) : Wither this is being invoked remotely, or locally. + * @params remote (Boolean) : Wither this is being invoked remotely, or locally. */ decayTextBoxById(theatreId, remote) { - let insert = this.getInsertById(theatreId); - let textBox = this._getTextBoxById(theatreId); + let insert = this.getInsertById(theatreId); + let textBox = this._getTextBoxById(theatreId); if (!textBox || !insert) return; - if (!remote && !this.isActorOwner(game.user.id,theatreId)) { + if (!remote && !this.isActorOwner(game.user.id, theatreId)) { ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.DoNotControl")); - return; + return; } // clear last speaking if present - KHelpers.removeClass(textBox,"theatre-text-box-lastspeaking"); - textBox.style.background = ""; - textBox.style["box-shadow"] = ""; + KHelpers.removeClass(textBox, "theatre-text-box-lastspeaking"); + textBox.style.background = ""; + textBox.style["box-shadow"] = ""; // clear decay Timout if present if (insert.decayTOId) { - window.clearTimeout(insert.decayTOId); - insert.decayTOId = null; + window.clearTimeout(insert.decayTOId); + insert.decayTOId = null; } // kill tweens for (let c of textBox.children) { - for (let sc of c.children) - TweenMax.killTweensOf(sc); - TweenMax.killTweensOf(c); + for (let sc of c.children) TweenMax.killTweensOf(sc); + TweenMax.killTweensOf(c); } - TweenMax.killTweensOf(textBox); + TweenMax.killTweensOf(textBox); // decay - TweenMax.to(textBox.children,0.5,{ - top: this.theatreBar.offsetHeight/2, + TweenMax.to(textBox.children, 0.5, { + top: this.theatreBar.offsetHeight / 2, opacity: 0, ease: Power0.easeNone, onComplete: function () { - textBox.textContent = ''; - } - }); + textBox.textContent = ""; + }, + }); // Push to socket our event if (!remote) { - Theatre.instance._sendSceneEvent("decaytext",{insertid : theatreId}); + Theatre.instance._sendSceneEvent("decaytext", { insertid: theatreId }); } } /** - * Applies the player color to the textbox as - * a box-shadow, and background highlight. + * Applies the player color to the textbox as + * a box-shadow, and background highlight. * * @params textBox (HTMLElement) : The textBox to apply the color to. - * @params userId (String) : The User's Id. - * @params color (String) : The CSS color string to use if available. + * @params userId (String) : The User's Id. + * @params color (String) : The CSS color string to use if available. */ - applyPlayerColorToTextBox(textBox,userId,color) { - //let user = game.users.get(userId); - //let userColor = user.color.replace("#",""); - color = color ? color.replace("#","") : null || "FFFFFF"; + applyPlayerColorToTextBox(textBox, userId, color) { + //let user = game.users.get(userId); + //let userColor = user.color.replace("#",""); + color = color ? color.replace("#", "") : null || "FFFFFF"; // break into radix - let red = parseInt(color.substring(0,2),16); - let green = parseInt(color.substring(2,4),16); - let blue = parseInt(color.substring(4),16); + let red = parseInt(color.substring(0, 2), 16); + let green = parseInt(color.substring(2, 4), 16); + let blue = parseInt(color.substring(4), 16); - let darkred = Math.max(red-50,0); - let darkgreen = Math.max(green-50,0); - let darkblue = Math.max(blue-50,0); + let darkred = Math.max(red - 50, 0); + let darkgreen = Math.max(green - 50, 0); + let darkblue = Math.max(blue - 50, 0); - red = Math.min(red+75,255); - green = Math.min(green+75,255); - blue = Math.min(blue+75,255); + red = Math.min(red + 75, 255); + green = Math.min(green + 75, 255); + blue = Math.min(blue + 75, 255); - if (Theatre.DEBUG) console.log("color %s : red: %s:%s, green %s:%s, blue %s:%s",color,red,darkred,green,darkgreen,blue,darkblue); + if (Theatre.DEBUG) console.log("color %s : red: %s:%s, green %s:%s, blue %s:%s", color, red, darkred, green, darkgreen, blue, darkblue); // style specific settings switch (this.settings.theatreStyle) { case "clearbox": - textBox.style.cssText += `background: linear-gradient(transparent 0%, rgba(${red},${green},${blue},0.30) 40%, rgba(${red},${green},${blue},0.30) 60%, transparent 100%); box-shadow: 0px 5px 2px 1px rgba(${darkred}, ${darkgreen}, ${darkblue}, 0.30)`; - break; + textBox.style.cssText += `background: linear-gradient(transparent 0%, rgba(${red},${green},${blue},0.30) 40%, rgba(${red},${green},${blue},0.30) 60%, transparent 100%); box-shadow: 0px 5px 2px 1px rgba(${darkred}, ${darkgreen}, ${darkblue}, 0.30)`; + break; case "mangabubble": case "lightbox": case "textbox": default: - textBox.style.cssText += `background: linear-gradient(transparent 0%, rgba(${red},${green},${blue},0.10) 40%, rgba(${red},${green},${blue},0.10) 60%, transparent 100%); box-shadow: 0px 5px 2px 1px rgba(${darkred}, ${darkgreen}, ${darkblue}, .2)`; - break; + textBox.style.cssText += `background: linear-gradient(transparent 0%, rgba(${red},${green},${blue},0.10) 40%, rgba(${red},${green},${blue},0.10) 60%, transparent 100%); box-shadow: 0px 5px 2px 1px rgba(${darkred}, ${darkgreen}, ${darkblue}, .2)`; + break; } - } /** * Gets the player 'flash' color that tints the insert as it 'pops. * - * @params userId (String) : The User's Id. - * @params color (String) : The CSS color string to use if available. + * @params userId (String) : The User's Id. + * @params color (String) : The CSS color string to use if available. * - * @return (String) : The CSS color to be used for the color flash. + * @return (String) : The CSS color to be used for the color flash. */ - getPlayerFlashColor(userId,color) { - //let user = game.users.get(userId); - //let userColor = user.color.replace("#",""); - color = color ? color.replace("#","") : null || "FFFFFF"; + getPlayerFlashColor(userId, color) { + //let user = game.users.get(userId); + //let userColor = user.color.replace("#",""); + color = color ? color.replace("#", "") : null || "FFFFFF"; // break into radix - let red = parseInt(color.substring(0,2),16); - let green = parseInt(color.substring(2,4),16); - let blue = parseInt(color.substring(4),16); + let red = parseInt(color.substring(0, 2), 16); + let green = parseInt(color.substring(2, 4), 16); + let blue = parseInt(color.substring(4), 16); // try to preserve ratios? - red = Math.min(red+75,255); - green = Math.min(green+75,255); - blue = Math.min(blue+75,255); + red = Math.min(red + 75, 255); + green = Math.min(green + 75, 255); + blue = Math.min(blue + 75, 255); - red = red.toString(16); - green = green.toString(16); - blue = blue.toString(16); + red = red.toString(16); + green = green.toString(16); + blue = blue.toString(16); - if (Theatre.DEBUG) console.log(`#${red}${green}${blue}`); - return `#${red}${green}${blue}`; + if (Theatre.DEBUG) console.log(`#${red}${green}${blue}`); + return `#${red}${green}${blue}`; } /** * Apply the font family to the given element * * @params elem (HTMLElement) : The HTMLElement to apply the font family to. - * @params fontFamily (String) : The name of the font family to add. + * @params fontFamily (String) : The name of the font family to add. * * @private */ - _applyFontFamily(elem,fontFamily) { + _applyFontFamily(elem, fontFamily) { elem.style["font-family"] = `"${fontFamily}", "SignikaBold", "Palatino Linotype", serif`; - elem.style["font-weight"] = this.fontWeight; + elem.style["font-weight"] = this.fontWeight; } /** * Toggle the narrator bar * * @param active (Boolean) : Wither to activate or deactive the narrator bar. - * @param remote (Boolean) : Winter this is being invoked remotely, or locally. + * @param remote (Boolean) : Winter this is being invoked remotely, or locally. */ - toggleNarratorBar(active,remote) { + toggleNarratorBar(active, remote) { if (active) { // spawn it let narratorBackdrop = Theatre.instance.theatreNarrator.getElementsByClassName("theatre-narrator-backdrop")[0]; - if (Theatre.DEBUG) console.log("NarratorBackdrop ",narratorBackdrop,Theatre.instance.theatreNarrator); - narratorBackdrop.style.width = "100%"; - Theatre.instance.theatreNarrator.style.opacity = "1"; - Theatre.instance.isNarratorActive = true; - // check if a navItem is active, if so, deactive it. + if (Theatre.DEBUG) console.log("NarratorBackdrop ", narratorBackdrop, Theatre.instance.theatreNarrator); + narratorBackdrop.style.width = "100%"; + Theatre.instance.theatreNarrator.style.opacity = "1"; + Theatre.instance.isNarratorActive = true; + // check if a navItem is active, if so, deactive it. // set speakingAs to "narrator" note that this will need heavy regression testing // as it'll be plugging into the insert workflow when it's truely not a real insert if (game.user.isGM) { - let btnNarrator = Theatre.instance.theatreControls.getElementsByClassName("theatre-icon-narrator")[0].parentNode; - let oldSpeakingItem = Theatre.instance.getNavItemById(Theatre.instance.speakingAs); - let oldSpeakingInsert = Theatre.instance.getInsertById(Theatre.instance.speakingAs); - let oldSpeakingLabel = Theatre.instance._getLabelFromInsert(oldSpeakingInsert); - - KHelpers.addClass(btnNarrator,"theatre-control-nav-bar-item-speakingas"); - if (oldSpeakingItem) - KHelpers.removeClass(oldSpeakingItem,"theatre-control-nav-bar-item-speakingas"); + let btnNarrator = Theatre.instance.theatreControls.getElementsByClassName("theatre-icon-narrator")[0].parentNode; + let oldSpeakingItem = Theatre.instance.getNavItemById(Theatre.instance.speakingAs); + let oldSpeakingInsert = Theatre.instance.getInsertById(Theatre.instance.speakingAs); + let oldSpeakingLabel = Theatre.instance._getLabelFromInsert(oldSpeakingInsert); + + KHelpers.addClass(btnNarrator, "theatre-control-nav-bar-item-speakingas"); + if (oldSpeakingItem) KHelpers.removeClass(oldSpeakingItem, "theatre-control-nav-bar-item-speakingas"); if (oldSpeakingInsert) { - oldSpeakingInsert.label.tint = 0xFFFFFF; - this._removeDockTween(this.speakingAs,null,"nameSpeakingPulse"); + oldSpeakingInsert.label.tint = 0xffffff; + this._removeDockTween(this.speakingAs, null, "nameSpeakingPulse"); } - let textFlyin = Theatre.instance.theatreNarrator.getAttribute("textflyin"); - let textStanding = Theatre.instance.theatreNarrator.getAttribute("textstanding"); - let textFont = Theatre.instance.theatreNarrator.getAttribute("textfont"); - let textSize = Theatre.instance.theatreNarrator.getAttribute("textsize"); - let textColor = Theatre.instance.theatreNarrator.getAttribute("textcolor"); - - Theatre.instance.theatreNarrator.setAttribute("textflyin", textFlyin ? textFlyin - : (Theatre.instance.userEmotes[game.user.id] ? Theatre.instance.userEmotes[game.user.id].textFlyin : null)) - Theatre.instance.theatreNarrator.setAttribute("textstanding", textStanding ? textStanding - : (Theatre.instance.userEmotes[game.user.id] ? Theatre.instance.userEmotes[game.user.id].textStanding : null)) - Theatre.instance.theatreNarrator.setAttribute("textfont", textFont ? textFont - : (Theatre.instance.userEmotes[game.user.id] ? Theatre.instance.userEmotes[game.user.id].textFont : null)) - Theatre.instance.theatreNarrator.setAttribute("textsize", textSize ? textSize - : (Theatre.instance.userEmotes[game.user.id] ? Theatre.instance.userEmotes[game.user.id].textSize : null)) - Theatre.instance.theatreNarrator.setAttribute("textcolor", textColor ? textColor - : (Theatre.instance.userEmotes[game.user.id] ? Theatre.instance.userEmotes[game.user.id].textColor : null)) - - let cimg = Theatre.instance.getTheatreCoverPortrait(); + let textFlyin = Theatre.instance.theatreNarrator.getAttribute("textflyin"); + let textStanding = Theatre.instance.theatreNarrator.getAttribute("textstanding"); + let textFont = Theatre.instance.theatreNarrator.getAttribute("textfont"); + let textSize = Theatre.instance.theatreNarrator.getAttribute("textsize"); + let textColor = Theatre.instance.theatreNarrator.getAttribute("textcolor"); + + Theatre.instance.theatreNarrator.setAttribute( + "textflyin", + textFlyin ? textFlyin : Theatre.instance.userEmotes[game.user.id] ? Theatre.instance.userEmotes[game.user.id].textFlyin : null + ); + Theatre.instance.theatreNarrator.setAttribute( + "textstanding", + textStanding ? textStanding : Theatre.instance.userEmotes[game.user.id] ? Theatre.instance.userEmotes[game.user.id].textStanding : null + ); + Theatre.instance.theatreNarrator.setAttribute( + "textfont", + textFont ? textFont : Theatre.instance.userEmotes[game.user.id] ? Theatre.instance.userEmotes[game.user.id].textFont : null + ); + Theatre.instance.theatreNarrator.setAttribute( + "textsize", + textSize ? textSize : Theatre.instance.userEmotes[game.user.id] ? Theatre.instance.userEmotes[game.user.id].textSize : null + ); + Theatre.instance.theatreNarrator.setAttribute( + "textcolor", + textColor ? textColor : Theatre.instance.userEmotes[game.user.id] ? Theatre.instance.userEmotes[game.user.id].textColor : null + ); + + let cimg = Theatre.instance.getTheatreCoverPortrait(); // clear cover - cimg.removeAttribute("src"); - cimg.style.opacity = "0"; + cimg.removeAttribute("src"); + cimg.style.opacity = "0"; // clear typing theatreId data - Theatre.instance.removeUserTyping(game.user.id); - Theatre.instance.usersTyping[game.user.id].theatreId = null; + Theatre.instance.removeUserTyping(game.user.id); + Theatre.instance.usersTyping[game.user.id].theatreId = null; // Mark speaking as Narrator - Theatre.instance.speakingAs = Theatre.NARRATOR; - Theatre.instance.setUserTyping(game.user.id,Theatre.NARRATOR); + Theatre.instance.speakingAs = Theatre.NARRATOR; + Theatre.instance.setUserTyping(game.user.id, Theatre.NARRATOR); // push focus to chat-message - let chatMessage = document.getElementById("chat-message"); - chatMessage.focus(); + let chatMessage = document.getElementById("chat-message"); + chatMessage.focus(); // send event to triggier the narrator bar - if (!remote) - Theatre.instance._sendSceneEvent("narrator",{active: true}); + if (!remote) Theatre.instance._sendSceneEvent("narrator", { active: true }); // re-render the emote menu (expensive) - Theatre.instance.renderEmoteMenu(); + Theatre.instance.renderEmoteMenu(); } } else { // remove it let narratorBackdrop = Theatre.instance.theatreNarrator.getElementsByClassName("theatre-narrator-backdrop")[0]; let narratorContent = Theatre.instance.theatreNarrator.getElementsByClassName("theatre-narrator-content")[0]; - if (Theatre.DEBUG) console.log("NarratorBackdrop ",narratorBackdrop,Theatre.instance.theatreNarrator); + if (Theatre.DEBUG) console.log("NarratorBackdrop ", narratorBackdrop, Theatre.instance.theatreNarrator); narratorBackdrop.style.width = "0%"; - Theatre.instance.theatreNarrator.style.opacity = "0"; - Theatre.instance.isNarratorActive = false; + Theatre.instance.theatreNarrator.style.opacity = "0"; + Theatre.instance.isNarratorActive = false; // kill animations for (let c of narratorContent.children) { - for (let sc of c.children) - TweenMax.killTweensOf(sc); - TweenMax.killTweensOf(c); + for (let sc of c.children) TweenMax.killTweensOf(sc); + TweenMax.killTweensOf(c); } - for (let c of narratorContent.children) - c.parentNode.removeChild(c); - TweenMax.killTweensOf(narratorContent); - narratorContent.style["overflow-y"] = "scroll"; - narratorContent.style["overflow-x"] = "hidden"; + for (let c of narratorContent.children) c.parentNode.removeChild(c); + TweenMax.killTweensOf(narratorContent); + narratorContent.style["overflow-y"] = "scroll"; + narratorContent.style["overflow-x"] = "hidden"; - if (Theatre.DEBUG) console.log("all tweens",TweenMax.getAllTweens()); - narratorContent.textContent = ''; + if (Theatre.DEBUG) console.log("all tweens", TweenMax.getAllTweens()); + narratorContent.textContent = ""; if (game.user.isGM) { - let btnNarrator = Theatre.instance.theatreControls.getElementsByClassName("theatre-icon-narrator")[0].parentNode; - KHelpers.removeClass(btnNarrator,"theatre-control-nav-bar-item-speakingas"); + let btnNarrator = Theatre.instance.theatreControls.getElementsByClassName("theatre-icon-narrator")[0].parentNode; + KHelpers.removeClass(btnNarrator, "theatre-control-nav-bar-item-speakingas"); // clear narrator - Theatre.instance.speakingAs = null; - Theatre.instance.removeUserTyping(game.user.id); - Theatre.instance.usersTyping[game.user.id].theatreId = null; + Theatre.instance.speakingAs = null; + Theatre.instance.removeUserTyping(game.user.id); + Theatre.instance.usersTyping[game.user.id].theatreId = null; // send event to turn off the narrator bar - if (!remote) - Theatre.instance._sendSceneEvent("narrator",{active: false}); + if (!remote) Theatre.instance._sendSceneEvent("narrator", { active: false }); // re-render the emote menu (expensive) - Theatre.instance.renderEmoteMenu(); + Theatre.instance.renderEmoteMenu(); } } - } /** @@ -5194,55 +5026,54 @@ class Theatre { renderEmoteMenu() { // each actor may have a different emote set // get actor emote set for currently speaking emote, else use the default set - let actorId = Theatre.instance.speakingAs ? Theatre.instance.speakingAs.replace("theatre-","") : null; - let insert = Theatre.instance.getInsertById(Theatre.instance.speakingAs); - let actor; - if (actorId) - actor = game.actors.get(actorId); - - let emotes = Theatre.getActorEmotes(actorId); - let fonts = Theatre.FONTS; - let textFlyin = Theatre.FLYIN_ANIMS; - let textStanding = Theatre.STANDING_ANIMS; - let sideBar = document.getElementById("sidebar"); - renderTemplate("modules/theatre/app/templates/emote_menu.html",{emotes,textFlyin,textStanding,fonts}).then(template=>{ - if (Theatre.DEBUG) console.log("emote window template rendered"); - Theatre.instance.theatreEmoteMenu.style.top = `${Theatre.instance.theatreControls.offsetTop-410}px`; - Theatre.instance.theatreEmoteMenu.innerHTML = template; + let actorId = Theatre.instance.speakingAs ? Theatre.instance.speakingAs.replace("theatre-", "") : null; + let insert = Theatre.instance.getInsertById(Theatre.instance.speakingAs); + let actor; + if (actorId) actor = game.actors.get(actorId); + + let emotes = Theatre.getActorEmotes(actorId); + let fonts = Theatre.FONTS; + let textFlyin = Theatre.FLYIN_ANIMS; + let textStanding = Theatre.STANDING_ANIMS; + let sideBar = document.getElementById("sidebar"); + renderTemplate("modules/theatre/app/templates/emote_menu.html", { emotes, textFlyin, textStanding, fonts }).then((template) => { + if (Theatre.DEBUG) console.log("emote window template rendered"); + Theatre.instance.theatreEmoteMenu.style.top = `${Theatre.instance.theatreControls.offsetTop - 410}px`; + Theatre.instance.theatreEmoteMenu.innerHTML = template; let wheelFunc = function (ev) { - //console.log("wheel on text-box",ev.currentTarget.scrollTop,ev.deltaY,ev.deltaMode); - let pos = ev.deltaY > 0; - ev.currentTarget.scrollTop += (pos ? 10 : -10); - ev.preventDefault(); - ev.stopPropagation(); - } + //console.log("wheel on text-box",ev.currentTarget.scrollTop,ev.deltaY,ev.deltaMode); + let pos = ev.deltaY > 0; + ev.currentTarget.scrollTop += pos ? 10 : -10; + ev.preventDefault(); + ev.stopPropagation(); + }; let wheelFunc2 = function (ev) { - //console.log("wheel on text-anim",ev.currentTarget.parentNode.scrollTop,ev.deltaY,ev.deltaMode); - let pos = ev.deltaY > 0; - ev.currentTarget.parentNode.scrollTop += (pos ? 10 : -10); - ev.preventDefault(); - ev.stopPropagation(); - } + //console.log("wheel on text-anim",ev.currentTarget.parentNode.scrollTop,ev.deltaY,ev.deltaMode); + let pos = ev.deltaY > 0; + ev.currentTarget.parentNode.scrollTop += pos ? 10 : -10; + ev.preventDefault(); + ev.stopPropagation(); + }; // bind handlers for the font/size/color selectors - let sizeSelect = Theatre.instance.theatreEmoteMenu.getElementsByClassName('sizeselect')[0]; - let colorSelect = Theatre.instance.theatreEmoteMenu.getElementsByClassName('colorselect')[0]; - let fontSelect = Theatre.instance.theatreEmoteMenu.getElementsByClassName('fontselect')[0]; - //console.log("Selectors found: ",sizeSelect,colorSelect,fontSelect); + let sizeSelect = Theatre.instance.theatreEmoteMenu.getElementsByClassName("sizeselect")[0]; + let colorSelect = Theatre.instance.theatreEmoteMenu.getElementsByClassName("colorselect")[0]; + let fontSelect = Theatre.instance.theatreEmoteMenu.getElementsByClassName("fontselect")[0]; + //console.log("Selectors found: ",sizeSelect,colorSelect,fontSelect); // assign font from insert if (insert && insert.textFont) { //if (fonts.includes(insert.textFont)) fontSelect.value = insert.textFont; - //else fontSelect.value = fonts[0]; - fontSelect.value = insert.textFont; + //else fontSelect.value = fonts[0]; + fontSelect.value = insert.textFont; } else if (Theatre.instance.userEmotes[game.user.id] && Theatre.instance.userEmotes[game.user.id].textFont) { - //if (fonts.includes(Theatre.instance.userEmotes[game.user.id].textFont)) - //fontSelect.value = Theatre.instance.userEmotes[game.user.id].textFont; - //else - //fontSelect.value = fonts[0]; - fontSelect.value = Theatre.instance.userEmotes[game.user.id].textFont; - if (insert) insert.textFont = fontSelect.value; + //if (fonts.includes(Theatre.instance.userEmotes[game.user.id].textFont)) + //fontSelect.value = Theatre.instance.userEmotes[game.user.id].textFont; + //else + //fontSelect.value = fonts[0]; + fontSelect.value = Theatre.instance.userEmotes[game.user.id].textFont; + if (insert) insert.textFont = fontSelect.value; } else { fontSelect.value = fonts[0]; } @@ -5250,160 +5081,148 @@ class Theatre { if (insert && insert.textColor) { colorSelect.value = insert.textColor; } else if (Theatre.instance.userEmotes[game.user.id] && Theatre.instance.userEmotes[game.user.id].textColor) { - colorSelect.value = Theatre.instance.userEmotes[game.user.id].textColor; - if (insert) insert.textColor = colorSelect.value; + colorSelect.value = Theatre.instance.userEmotes[game.user.id].textColor; + if (insert) insert.textColor = colorSelect.value; } // assgin font size - let sizeIcon = document.createElement("div"); - let sizeValue = 2; - if (insert) - sizeValue = insert.textSize; - else if (Theatre.instance.userEmotes[game.user.id]) - sizeValue = Theatre.instance.userEmotes[game.user.id].textSize; + let sizeIcon = document.createElement("div"); + let sizeValue = 2; + if (insert) sizeValue = insert.textSize; + else if (Theatre.instance.userEmotes[game.user.id]) sizeValue = Theatre.instance.userEmotes[game.user.id].textSize; switch (sizeValue) { case 3: - KHelpers.addClass(sizeIcon,"theatre-icon-fontsize-large"); + KHelpers.addClass(sizeIcon, "theatre-icon-fontsize-large"); break; case 1: - KHelpers.addClass(sizeIcon,"theatre-icon-fontsize-small"); + KHelpers.addClass(sizeIcon, "theatre-icon-fontsize-small"); break; default: - KHelpers.addClass(sizeIcon,"theatre-icon-fontsize-medium"); - break; + KHelpers.addClass(sizeIcon, "theatre-icon-fontsize-medium"); + break; } - sizeSelect.appendChild(sizeIcon); - - sizeSelect.addEventListener("click",ev=>{ - - let insert = Theatre.instance.getInsertById(Theatre.instance.speakingAs); - let icon = sizeSelect.children[0]; - let value = 2; - if (insert) - value = insert.textSize; - else if (Theatre.instance.userEmotes[game.user.id]) - value = Theatre.instance.userEmotes[game.user.id].textSize; + sizeSelect.appendChild(sizeIcon); + sizeSelect.addEventListener("click", (ev) => { + let insert = Theatre.instance.getInsertById(Theatre.instance.speakingAs); + let icon = sizeSelect.children[0]; + let value = 2; + if (insert) value = insert.textSize; + else if (Theatre.instance.userEmotes[game.user.id]) value = Theatre.instance.userEmotes[game.user.id].textSize; switch (value) { case 3: - KHelpers.removeClass(icon,"theatre-icon-fontsize-large"); - KHelpers.addClass(icon,"theatre-icon-fontsize-medium"); - value = 2; + KHelpers.removeClass(icon, "theatre-icon-fontsize-large"); + KHelpers.addClass(icon, "theatre-icon-fontsize-medium"); + value = 2; break; case 1: - KHelpers.removeClass(icon,"theatre-icon-fontsize-small"); - KHelpers.addClass(icon,"theatre-icon-fontsize-large"); - value = 3; + KHelpers.removeClass(icon, "theatre-icon-fontsize-small"); + KHelpers.addClass(icon, "theatre-icon-fontsize-large"); + value = 3; break; default: - KHelpers.removeClass(icon,"theatre-icon-fontsize-medium"); - KHelpers.addClass(icon,"theatre-icon-fontsize-small"); - value = 1; - break; + KHelpers.removeClass(icon, "theatre-icon-fontsize-medium"); + KHelpers.addClass(icon, "theatre-icon-fontsize-small"); + value = 1; + break; } - Theatre.instance.setUserEmote(game.user.id,Theatre.instance.speakingAs,'textsize',value); - }); - fontSelect.addEventListener("change",ev=>{ - Theatre.instance.setUserEmote(game.user.id,Theatre.instance.speakingAs,'textfont',ev.currentTarget.value); - Theatre.instance.renderEmoteMenu(); - }); - colorSelect.addEventListener("change",ev=>{ - Theatre.instance.setUserEmote(game.user.id,Theatre.instance.speakingAs,'textcolor',ev.currentTarget.value); - }); - + Theatre.instance.setUserEmote(game.user.id, Theatre.instance.speakingAs, "textsize", value); + }); + fontSelect.addEventListener("change", (ev) => { + Theatre.instance.setUserEmote(game.user.id, Theatre.instance.speakingAs, "textfont", ev.currentTarget.value); + Theatre.instance.renderEmoteMenu(); + }); + colorSelect.addEventListener("change", (ev) => { + Theatre.instance.setUserEmote(game.user.id, Theatre.instance.speakingAs, "textcolor", ev.currentTarget.value); + }); // Apply our language specific fonts to the template // OR apply the font specified by the insert - let headers = Theatre.instance.theatreEmoteMenu.getElementsByTagName('h2'); - let textAnims = Theatre.instance.theatreEmoteMenu.getElementsByClassName('textanim'); - for (let e of headers) - Theatre.instance._applyFontFamily(e,Theatre.instance.titleFont); + let headers = Theatre.instance.theatreEmoteMenu.getElementsByTagName("h2"); + let textAnims = Theatre.instance.theatreEmoteMenu.getElementsByClassName("textanim"); + for (let e of headers) Theatre.instance._applyFontFamily(e, Theatre.instance.titleFont); for (let e of textAnims) { - let font = fontSelect.value; - Theatre.instance._applyFontFamily(e, font); - e.addEventListener("wheel",wheelFunc2); + let font = fontSelect.value; + Theatre.instance._applyFontFamily(e, font); + e.addEventListener("wheel", wheelFunc2); } // bind click listeners for the textanim elements to animate a preview // hover-off will reset the text content - let flyinBox = Theatre.instance.theatreEmoteMenu.getElementsByClassName("textflyin-box")[0]; - flyinBox = flyinBox.getElementsByClassName("theatre-container-column")[0]; - let standingBox = Theatre.instance.theatreEmoteMenu.getElementsByClassName("textstanding-box")[0]; - standingBox = standingBox.getElementsByClassName("theatre-container-column")[0]; - - flyinBox.addEventListener("wheel",wheelFunc); - standingBox.addEventListener("wheel",wheelFunc) + let flyinBox = Theatre.instance.theatreEmoteMenu.getElementsByClassName("textflyin-box")[0]; + flyinBox = flyinBox.getElementsByClassName("theatre-container-column")[0]; + let standingBox = Theatre.instance.theatreEmoteMenu.getElementsByClassName("textstanding-box")[0]; + standingBox = standingBox.getElementsByClassName("theatre-container-column")[0]; + flyinBox.addEventListener("wheel", wheelFunc); + standingBox.addEventListener("wheel", wheelFunc); for (let child of flyinBox.children) { // get animation function // bind annonomous click listener child.addEventListener("mouseover", (ev) => { - let text = ev.currentTarget.getAttribute("otext"); - let anim = ev.currentTarget.getAttribute("name"); - //console.log("child text: ",text,ev.currentTarget); - ev.currentTarget.textContent = ""; - let charSpans = Theatre.splitTextBoxToChars(text,ev.currentTarget); - textFlyin[anim].func.call(this,charSpans,0.5,0.05,null); - }); + let text = ev.currentTarget.getAttribute("otext"); + let anim = ev.currentTarget.getAttribute("name"); + //console.log("child text: ",text,ev.currentTarget); + ev.currentTarget.textContent = ""; + let charSpans = Theatre.splitTextBoxToChars(text, ev.currentTarget); + textFlyin[anim].func.call(this, charSpans, 0.5, 0.05, null); + }); child.addEventListener("mouseout", (ev) => { for (let c of ev.currentTarget.children) { - for (let sc of c.children) - TweenMax.killTweensOf(sc); - TweenMax.killTweensOf(c); + for (let sc of c.children) TweenMax.killTweensOf(sc); + TweenMax.killTweensOf(c); } - for (let c of ev.currentTarget.children) - c.parentNode.removeChild(c); - TweenMax.killTweensOf(child); - child.style["overflow-y"] = "scroll"; - child.style["overflow-x"] = "hidden"; - //console.log("all tweens",TweenMax.getAllTweens()); - ev.currentTarget.textContent = ev.currentTarget.getAttribute("otext"); - }); + for (let c of ev.currentTarget.children) c.parentNode.removeChild(c); + TweenMax.killTweensOf(child); + child.style["overflow-y"] = "scroll"; + child.style["overflow-x"] = "hidden"; + //console.log("all tweens",TweenMax.getAllTweens()); + ev.currentTarget.textContent = ev.currentTarget.getAttribute("otext"); + }); // bind text anim type child.addEventListener("mouseup", (ev) => { if (ev.button == 0) { - if (KHelpers.hasClass(ev.currentTarget,"textflyin-active")) { - KHelpers.removeClass(ev.currentTarget,"textflyin-active"); - Theatre.instance.setUserEmote(game.user.id,Theatre.instance.speakingAs,'textflyin',null); + if (KHelpers.hasClass(ev.currentTarget, "textflyin-active")) { + KHelpers.removeClass(ev.currentTarget, "textflyin-active"); + Theatre.instance.setUserEmote(game.user.id, Theatre.instance.speakingAs, "textflyin", null); } else { - let lastActives = Theatre.instance.theatreEmoteMenu.getElementsByClassName("textflyin-active"); - for (let la of lastActives) - KHelpers.removeClass(la,"textflyin-active"); + let lastActives = Theatre.instance.theatreEmoteMenu.getElementsByClassName("textflyin-active"); + for (let la of lastActives) KHelpers.removeClass(la, "textflyin-active"); //if (insert || Theatre.instance.speakingAs == Theatre.NARRATOR) { - KHelpers.addClass(ev.currentTarget,"textflyin-active"); - Theatre.instance.setUserEmote(game.user.id,Theatre.instance.speakingAs,'textflyin',ev.currentTarget.getAttribute("name")); + KHelpers.addClass(ev.currentTarget, "textflyin-active"); + Theatre.instance.setUserEmote(game.user.id, Theatre.instance.speakingAs, "textflyin", ev.currentTarget.getAttribute("name")); //} } // push focus to chat-message - let chatMessage = document.getElementById("chat-message"); - chatMessage.focus(); + let chatMessage = document.getElementById("chat-message"); + chatMessage.focus(); } - }); - // check if this child is our configured 'text style' - let childTextMode = child.getAttribute("name"); + }); + // check if this child is our configured 'text style' + let childTextMode = child.getAttribute("name"); if (insert) { - let insertTextMode = insert.textFlyin; + let insertTextMode = insert.textFlyin; if (insertTextMode && insertTextMode == childTextMode) { - KHelpers.addClass(child,"textflyin-active"); + KHelpers.addClass(child, "textflyin-active"); // scroll to //TweenMax.to(flyinBox,.4,{scrollTo:{y:child.offsetTop, offsetY:flyinBox.offsetHeight/2}}) - flyinBox.scrollTop = child.offsetTop-Math.max(flyinBox.offsetHeight/2,0); + flyinBox.scrollTop = child.offsetTop - Math.max(flyinBox.offsetHeight / 2, 0); } } else if (Theatre.instance.speakingAs == Theatre.NARRATOR) { - let insertTextMode = Theatre.instance.theatreNarrator.getAttribute("textflyin"); + let insertTextMode = Theatre.instance.theatreNarrator.getAttribute("textflyin"); if (insertTextMode && insertTextMode == childTextMode) { - KHelpers.addClass(child,"textflyin-active"); + KHelpers.addClass(child, "textflyin-active"); // scroll to //TweenMax.to(flyinBox,.4,{scrollTo:{y:child.offsetTop, offsetY:flyinBox.offsetHeight/2}}) - flyinBox.scrollTop = child.offsetTop-Math.max(flyinBox.offsetHeight/2,0); + flyinBox.scrollTop = child.offsetTop - Math.max(flyinBox.offsetHeight / 2, 0); } - } else if (!insert && Theatre.instance.userEmotes[game.user.id] && (child.getAttribute("name") == Theatre.instance.userEmotes[game.user.id].textFlyin)) { - KHelpers.addClass(child,"textflyin-active"); + } else if (!insert && Theatre.instance.userEmotes[game.user.id] && child.getAttribute("name") == Theatre.instance.userEmotes[game.user.id].textFlyin) { + KHelpers.addClass(child, "textflyin-active"); // scroll to //TweenMax.to(flyinBox,.4,{scrollTo:{y:child.offsetTop, offsetY:flyinBox.offsetHeight/2}}) - flyinBox.scrollTop = child.offsetTop-Math.max(flyinBox.offsetHeight/2,0); + flyinBox.scrollTop = child.offsetTop - Math.max(flyinBox.offsetHeight / 2, 0); } } @@ -5411,140 +5230,131 @@ class Theatre { // get animation function // bind annonomous click listener child.addEventListener("mouseover", (ev) => { - let text = ev.currentTarget.getAttribute("otext"); - let anim = ev.currentTarget.getAttribute("name"); - //console.log("child text: ",text,ev.currentTarget); - ev.currentTarget.textContent = ""; - let charSpans = Theatre.splitTextBoxToChars(text,ev.currentTarget); - textFlyin["typewriter"].func.call(this,charSpans,0.5,0.05,(textStanding[anim] ? textStanding[anim].func : null)); - }); + let text = ev.currentTarget.getAttribute("otext"); + let anim = ev.currentTarget.getAttribute("name"); + //console.log("child text: ",text,ev.currentTarget); + ev.currentTarget.textContent = ""; + let charSpans = Theatre.splitTextBoxToChars(text, ev.currentTarget); + textFlyin["typewriter"].func.call(this, charSpans, 0.5, 0.05, textStanding[anim] ? textStanding[anim].func : null); + }); child.addEventListener("mouseout", (ev) => { for (let c of ev.currentTarget.children) { - for (let sc of c.children) - TweenMax.killTweensOf(sc); - TweenMax.killTweensOf(c); + for (let sc of c.children) TweenMax.killTweensOf(sc); + TweenMax.killTweensOf(c); } - for (let c of ev.currentTarget.children) - c.parentNode.removeChild(c); - TweenMax.killTweensOf(child); - child.style["overflow-y"] = "scroll"; - child.style["overflow-x"] = "hidden"; - //console.log("all tweens",TweenMax.getAllTweens()); - ev.currentTarget.textContent = ev.currentTarget.getAttribute("otext"); - }); + for (let c of ev.currentTarget.children) c.parentNode.removeChild(c); + TweenMax.killTweensOf(child); + child.style["overflow-y"] = "scroll"; + child.style["overflow-x"] = "hidden"; + //console.log("all tweens",TweenMax.getAllTweens()); + ev.currentTarget.textContent = ev.currentTarget.getAttribute("otext"); + }); // bind text anim type child.addEventListener("mouseup", (ev) => { if (ev.button == 0) { - if (KHelpers.hasClass(ev.currentTarget,"textstanding-active")) { - KHelpers.removeClass(ev.currentTarget,"textstanding-active"); - Theatre.instance.setUserEmote(game.user.id,Theatre.instance.speakingAs,'textstanding',null); + if (KHelpers.hasClass(ev.currentTarget, "textstanding-active")) { + KHelpers.removeClass(ev.currentTarget, "textstanding-active"); + Theatre.instance.setUserEmote(game.user.id, Theatre.instance.speakingAs, "textstanding", null); } else { - let lastActives = Theatre.instance.theatreEmoteMenu.getElementsByClassName("textstanding-active"); - for (let la of lastActives) - KHelpers.removeClass(la,"textstanding-active"); + let lastActives = Theatre.instance.theatreEmoteMenu.getElementsByClassName("textstanding-active"); + for (let la of lastActives) KHelpers.removeClass(la, "textstanding-active"); //if (insert || Theatre.instance.speakingAs == Theatre.NARRATOR) { - KHelpers.addClass(ev.currentTarget,"textstanding-active"); - Theatre.instance.setUserEmote(game.user.id,Theatre.instance.speakingAs,'textstanding',ev.currentTarget.getAttribute("name")); + KHelpers.addClass(ev.currentTarget, "textstanding-active"); + Theatre.instance.setUserEmote(game.user.id, Theatre.instance.speakingAs, "textstanding", ev.currentTarget.getAttribute("name")); //} } // push focus to chat-message - let chatMessage = document.getElementById("chat-message"); - chatMessage.focus(); + let chatMessage = document.getElementById("chat-message"); + chatMessage.focus(); } - }); - // check if this child is our configured 'text style' - let childTextMode = child.getAttribute("name"); + }); + // check if this child is our configured 'text style' + let childTextMode = child.getAttribute("name"); if (insert) { - let insertTextMode = insert.textStanding; + let insertTextMode = insert.textStanding; if (insertTextMode && insertTextMode == childTextMode) { - KHelpers.addClass(child,"textstanding-active"); + KHelpers.addClass(child, "textstanding-active"); //TweenMax.to(standingBox,.4,{scrollTo:{y:child.offsetTop, offsetY:standingBox.offsetHeight/2}}) - standingBox.scrollTop = child.offsetTop-Math.max(standingBox.offsetHeight/2,0); + standingBox.scrollTop = child.offsetTop - Math.max(standingBox.offsetHeight / 2, 0); } } else if (Theatre.instance.speakingAs == Theatre.NARRATOR) { - let insertTextMode = Theatre.instance.theatreNarrator.getAttribute("textstanding"); + let insertTextMode = Theatre.instance.theatreNarrator.getAttribute("textstanding"); if (insertTextMode && insertTextMode == childTextMode) { - KHelpers.addClass(child,"textstanding-active"); + KHelpers.addClass(child, "textstanding-active"); // scroll to //TweenMax.to(standingBox,.4,{scrollTo:{y:child.offsetTop, offsetY:standingBox.offsetHeight/2}}) - standingBox.scrollTop = child.offsetTop-Math.max(standingBox.offsetHeight/2,0); + standingBox.scrollTop = child.offsetTop - Math.max(standingBox.offsetHeight / 2, 0); } - } else if (Theatre.instance.userEmotes[game.user.id] && (child.getAttribute("name") == Theatre.instance.userEmotes[game.user.id].textStanding)) { - KHelpers.addClass(child,"textstanding-active"); + } else if (Theatre.instance.userEmotes[game.user.id] && child.getAttribute("name") == Theatre.instance.userEmotes[game.user.id].textStanding) { + KHelpers.addClass(child, "textstanding-active"); // scroll to //TweenMax.to(standingBox,.4,{scrollTo:{y:child.offsetTop, offsetY:standingBox.offsetHeight/2}}) - standingBox.scrollTop = child.offsetTop-Math.max(standingBox.offsetHeight/2,0); + standingBox.scrollTop = child.offsetTop - Math.max(standingBox.offsetHeight / 2, 0); } } // If speaking as theatre, minimize away the emote section - let emoteBox = Theatre.instance.theatreEmoteMenu.getElementsByClassName("emote-box")[0]; - let emContainer = emoteBox.getElementsByClassName("theatre-container-tiles")[0]; + let emoteBox = Theatre.instance.theatreEmoteMenu.getElementsByClassName("emote-box")[0]; + let emContainer = emoteBox.getElementsByClassName("theatre-container-tiles")[0]; if (Theatre.instance.speakingAs == Theatre.NARRATOR) { - emoteBox.style.cssText += "flex: 0 0 40px"; - let emLabel = emoteBox.getElementsByTagName("h2")[0]; - fontSelect.style["max-width"] = "unset"; - emContainer.style.display = "none"; - emLabel.style.display = "none"; + emoteBox.style.cssText += "flex: 0 0 40px"; + let emLabel = emoteBox.getElementsByTagName("h2")[0]; + fontSelect.style["max-width"] = "unset"; + emContainer.style.display = "none"; + emLabel.style.display = "none"; } else { // configure handles to bind emote selection - let emoteBtns = Theatre.instance.theatreEmoteMenu.getElementsByClassName("emote"); + let emoteBtns = Theatre.instance.theatreEmoteMenu.getElementsByClassName("emote"); for (let child of emoteBtns) { //bind annomous click listener child.addEventListener("mouseup", (ev) => { if (ev.button == 0) { - let emName = ev.currentTarget.getAttribute("name"); - if (Theatre.DEBUG) console.log("em name: %s was clicked",emName); - if (KHelpers.hasClass(ev.currentTarget,"emote-active")) { - KHelpers.removeClass(ev.currentTarget,"emote-active"); + let emName = ev.currentTarget.getAttribute("name"); + if (Theatre.DEBUG) console.log("em name: %s was clicked", emName); + if (KHelpers.hasClass(ev.currentTarget, "emote-active")) { + KHelpers.removeClass(ev.currentTarget, "emote-active"); // if speaking set to base - Theatre.instance.setUserEmote(game.user.id,Theatre.instance.speakingAs,'emote',null); + Theatre.instance.setUserEmote(game.user.id, Theatre.instance.speakingAs, "emote", null); } else { - let lastActives = Theatre.instance.theatreEmoteMenu.getElementsByClassName("emote-active"); - for (let la of lastActives) - KHelpers.removeClass(la,"emote-active"); - KHelpers.addClass(ev.currentTarget,"emote-active"); + let lastActives = Theatre.instance.theatreEmoteMenu.getElementsByClassName("emote-active"); + for (let la of lastActives) KHelpers.removeClass(la, "emote-active"); + KHelpers.addClass(ev.currentTarget, "emote-active"); // if speaking, then set our emote! - Theatre.instance.setUserEmote(game.user.id,Theatre.instance.speakingAs,'emote',emName); + Theatre.instance.setUserEmote(game.user.id, Theatre.instance.speakingAs, "emote", emName); } // push focus to chat-message - let chatMessage = document.getElementById("chat-message"); - chatMessage.focus(); + let chatMessage = document.getElementById("chat-message"); + chatMessage.focus(); } - }); + }); // bind mouseenter Listener child.addEventListener("mouseenter", (ev) => { - Theatre.instance.configureTheatreToolTip(Theatre.instance.speakingAs,ev.currentTarget.getAttribute("name")); - }); + Theatre.instance.configureTheatreToolTip(Theatre.instance.speakingAs, ev.currentTarget.getAttribute("name")); + }); // check if this child is our configured 'emote' - let childEmote = child.getAttribute("name"); + let childEmote = child.getAttribute("name"); if (insert) { // if we have an insert we're speaking through, we should get that emote state instead // if the insert has no emote state, neither should we despite user settings - let insertEmote = insert.emote; + let insertEmote = insert.emote; if (insertEmote && insertEmote == childEmote) { - KHelpers.addClass(child,"emote-active"); - //emContainer.scrollTop = child.offsetTop-Math.max(emContainer.offsetHeight/2,0); + KHelpers.addClass(child, "emote-active"); + //emContainer.scrollTop = child.offsetTop-Math.max(emContainer.offsetHeight/2,0); } // we should 'highlight' emotes that at least have a base insert - if (emotes[childEmote] && emotes[childEmote].insert) - KHelpers.addClass(child,"emote-imgavail"); - + if (emotes[childEmote] && emotes[childEmote].insert) KHelpers.addClass(child, "emote-imgavail"); } - if (!insert && Theatre.instance.userEmotes[game.user.id] && (childEmote == Theatre.instance.userEmotes[game.user.id].emote)) { - KHelpers.addClass(child,"emote-active"); - //emContainer.scrollTop = child.offsetTop-Math.max(emContainer.offsetHeight/2,0); + if (!insert && Theatre.instance.userEmotes[game.user.id] && childEmote == Theatre.instance.userEmotes[game.user.id].emote) { + KHelpers.addClass(child, "emote-active"); + //emContainer.scrollTop = child.offsetTop-Math.max(emContainer.offsetHeight/2,0); } } // bind mouseleave Listener emoteBtns[0].parentNode.addEventListener("mouseleave", (ev) => { - Theatre.instance.theatreToolTip.style.opacity = 0; + Theatre.instance.theatreToolTip.style.opacity = 0; }); } - - - - }); + }); } /** @@ -5562,50 +5372,44 @@ class Theatre { */ handleWindowResize(ev) { //Theatre.instance.theatreDock.style.width = `calc(100% - ${document.getElementById("sidebar").offsetWidth+2}px)`; - let sideBar = document.getElementById("sidebar"); - Theatre.instance.theatreBar.style.width = (ui.sidebar._collapsed ? "100%" : `calc(100% - ${sideBar.offsetWidth+2}px)`); - Theatre.instance.theatreNarrator.style.width = (ui.sidebar._collapsed ? "100%" : `calc(100% - ${sideBar.offsetWidth+2}px)`); - let primeBar = document.getElementById("theatre-prime-bar"); + let sideBar = document.getElementById("sidebar"); + Theatre.instance.theatreBar.style.width = ui.sidebar._collapsed ? "100%" : `calc(100% - ${sideBar.offsetWidth + 2}px)`; + Theatre.instance.theatreNarrator.style.width = ui.sidebar._collapsed ? "100%" : `calc(100% - ${sideBar.offsetWidth + 2}px)`; + let primeBar = document.getElementById("theatre-prime-bar"); let secondBar = document.getElementById("theatre-second-bar"); if (Theatre.instance._getTextBoxes().length == 2) { - let dualWidth = Math.min(Math.floor(Theatre.instance.theatreBar.offsetWidth/2),650); - primeBar.style.width = dualWidth + "px"; - secondBar.style.width = dualWidth + "px"; - secondBar.style.left = `calc(100% - ${dualWidth}px)`; + let dualWidth = Math.min(Math.floor(Theatre.instance.theatreBar.offsetWidth / 2), 650); + primeBar.style.width = dualWidth + "px"; + secondBar.style.width = dualWidth + "px"; + secondBar.style.left = `calc(100% - ${dualWidth}px)`; } // emote menu - if (Theatre.instance.theatreEmoteMenu) - Theatre.instance.theatreEmoteMenu.style.top = `${Theatre.instance.theatreControls.offsetTop-410}px` + if (Theatre.instance.theatreEmoteMenu) Theatre.instance.theatreEmoteMenu.style.top = `${Theatre.instance.theatreControls.offsetTop - 410}px`; /* Theatre.instance.theatreToolTip.style.top = `${Theatre.instance.theatreControls.offsetTop-Theatre.instance.theatreToolTip.offsetHeight}px` Theatre.instance.theatreToolTip.style.left = `${sideBar.offsetLeft - Theatre.instance.theatreToolTip.offsetWidth}px` */ - let app = Theatre.instance.pixiCTX; - let dockWidth = Theatre.instance.theatreDock.offsetWidth; - let dockHeight = Theatre.instance.theatreDock.offsetHeight; - Theatre.instance.theatreDock.setAttribute("width",dockWidth); - Theatre.instance.theatreDock.setAttribute("height",dockHeight); + let app = Theatre.instance.pixiCTX; + let dockWidth = Theatre.instance.theatreDock.offsetWidth; + let dockHeight = Theatre.instance.theatreDock.offsetHeight; + Theatre.instance.theatreDock.setAttribute("width", dockWidth); + Theatre.instance.theatreDock.setAttribute("height", dockHeight); app.width = dockWidth; - app.height = dockHeight; - app.renderer.view.width = dockWidth; - app.renderer.view.height = dockHeight; - app.renderer.resize(dockWidth,dockHeight); - //app.render(); - if (!Theatre.instance.rendering) - Theatre.instance._renderTheatre(performance.now()); - - if (Theatre.instance.reorderTOId) - window.clearTimeout(Theatre.instance.reorderTOId) - - Theatre.instance.reorderTOId = window.setTimeout(()=>{ - Theatre.reorderInserts(); - Theatre.instance.reorderTOId = null; - },250); - - } + app.height = dockHeight; + app.renderer.view.width = dockWidth; + app.renderer.view.height = dockHeight; + app.renderer.resize(dockWidth, dockHeight); + //app.render(); + if (!Theatre.instance.rendering) Theatre.instance._renderTheatre(performance.now()); + if (Theatre.instance.reorderTOId) window.clearTimeout(Theatre.instance.reorderTOId); + Theatre.instance.reorderTOId = window.setTimeout(() => { + Theatre.reorderInserts(); + Theatre.instance.reorderTOId = null; + }, 250); + } /** * Store mouse position for our tooltip which will roam @@ -5613,12 +5417,11 @@ class Theatre { * @param ev (Event) : The Event that triggered the mouse move. */ handleEmoteMenuMouseMove(ev) { - Theatre.instance.theatreToolTip.style.top = - `${(ev.clientY || ev.pageY) - Theatre.instance.theatreToolTip.offsetHeight - 20}px`; - Theatre.instance.theatreToolTip.style.left = - `${Math.min( - (ev.clientX || ev.pageX) - Theatre.instance.theatreToolTip.offsetWidth/2, - Theatre.instance.theatreDock.offsetWidth-Theatre.instance.theatreToolTip.offsetWidth)}px`; + Theatre.instance.theatreToolTip.style.top = `${(ev.clientY || ev.pageY) - Theatre.instance.theatreToolTip.offsetHeight - 20}px`; + Theatre.instance.theatreToolTip.style.left = `${Math.min( + (ev.clientX || ev.pageX) - Theatre.instance.theatreToolTip.offsetWidth / 2, + Theatre.instance.theatreDock.offsetWidth - Theatre.instance.theatreToolTip.offsetWidth + )}px`; } /** @@ -5627,15 +5430,15 @@ class Theatre { * @param ev (Event) : The Event that triggered this handler */ handleBtnEmoteClick(ev) { - if (Theatre.DEBUG) console.log("emote click"); + if (Theatre.DEBUG) console.log("emote click"); - if (KHelpers.hasClass(ev.currentTarget,"theatre-control-btn-down")) { - Theatre.instance.theatreEmoteMenu.style.display = "none"; - KHelpers.removeClass(ev.currentTarget,"theatre-control-btn-down"); + if (KHelpers.hasClass(ev.currentTarget, "theatre-control-btn-down")) { + Theatre.instance.theatreEmoteMenu.style.display = "none"; + KHelpers.removeClass(ev.currentTarget, "theatre-control-btn-down"); } else { - Theatre.instance.renderEmoteMenu(); - Theatre.instance.theatreEmoteMenu.style.display = "flex"; - KHelpers.addClass(ev.currentTarget,"theatre-control-btn-down"); + Theatre.instance.renderEmoteMenu(); + Theatre.instance.theatreEmoteMenu.style.display = "flex"; + KHelpers.addClass(ev.currentTarget, "theatre-control-btn-down"); } } @@ -5645,7 +5448,7 @@ class Theatre { * @param ev (Event) : The Event that triggered this handler */ handleChatMessageFocusOut(ev) { - KHelpers.removeClass(Theatre.instance.theatreChatCover,"theatre-control-chat-cover-ooc"); + KHelpers.removeClass(Theatre.instance.theatreChatCover, "theatre-control-chat-cover-ooc"); } /** @@ -5654,10 +5457,12 @@ class Theatre { * @param ev (Event) : The Event that triggered this handler */ handleChatMessageKeyUp(ev) { - if (!ev.repeat - //&& Theatre.instance.speakingAs - && ev.key == "Control") - KHelpers.removeClass(Theatre.instance.theatreChatCover,"theatre-control-chat-cover-ooc"); + if ( + !ev.repeat && + //&& Theatre.instance.speakingAs + ev.key == "Control" + ) + KHelpers.removeClass(Theatre.instance.theatreChatCover, "theatre-control-chat-cover-ooc"); } /** @@ -5674,43 +5479,41 @@ class Theatre { action.onDown.call(context); } - let now = Date.now(); + let now = Date.now(); - if (!ev.repeat - //&& Theatre.instance.speakingAs - && ev.key == "Control") - KHelpers.addClass(Theatre.instance.theatreChatCover,"theatre-control-chat-cover-ooc"); + if ( + !ev.repeat && + //&& Theatre.instance.speakingAs + ev.key == "Control" + ) + KHelpers.addClass(Theatre.instance.theatreChatCover, "theatre-control-chat-cover-ooc"); - if (now - Theatre.instance.lastTyping < 3000) return; - if (ev.key == "Enter" - || ev.key == "Alt" - || ev.key == "Shift" - || ev.key == "Control") return; - if (Theatre.DEBUG) console.log("keydown in chat-message"); - Theatre.instance.lastTyping = now; - Theatre.instance.setUserTyping(game.user.id,Theatre.instance.speakingAs) - Theatre.instance._sendTypingEvent(); + if (now - Theatre.instance.lastTyping < 3000) return; + if (ev.key == "Enter" || ev.key == "Alt" || ev.key == "Shift" || ev.key == "Control") return; + if (Theatre.DEBUG) console.log("keydown in chat-message"); + Theatre.instance.lastTyping = now; + Theatre.instance.setUserTyping(game.user.id, Theatre.instance.speakingAs); + Theatre.instance._sendTypingEvent(); } - /** - * Handle the narrator click + * Handle the narrator click * * NOTE: this has issues with multiple GMs since the narrator bar currently works as a * "shim" in that it pretends to be a proper insert for text purposes only. - * + * * If another GM activates another charater, it will minimize the bar for a GM that is trying * to use the bar * * @param ev (Event) : The Event that triggered this handler */ handleBtnNarratorClick(ev) { - if (Theatre.DEBUG) console.log("narrator click"); + if (Theatre.DEBUG) console.log("narrator click"); - if (KHelpers.hasClass(ev.currentTarget,"theatre-control-nav-bar-item-speakingas")) { - Theatre.instance.toggleNarratorBar(false); + if (KHelpers.hasClass(ev.currentTarget, "theatre-control-nav-bar-item-speakingas")) { + Theatre.instance.toggleNarratorBar(false); } else { - Theatre.instance.toggleNarratorBar(true); + Theatre.instance.toggleNarratorBar(true); } } @@ -5720,7 +5523,7 @@ class Theatre { * @param ev (Event) : The Event that triggered this handler */ handleBtnCinemaClick(ev) { - if (Theatre.DEBUG) console.log("cinema click"); + if (Theatre.DEBUG) console.log("cinema click"); ui.notifications.info(game.i18n.localize("Theatre.NotYet")); /* if (KHelpers.hasClass(ev.currentTarget,"theatre-control-small-btn-down")) { @@ -5738,43 +5541,38 @@ class Theatre { * @param ev (Event) : The Event that triggered this handler */ handleBtnDelayEmoteClick(ev) { - if (Theatre.DEBUG) console.log("delay emote click"); + if (Theatre.DEBUG) console.log("delay emote click"); if (Theatre.instance.isDelayEmote) { - if (KHelpers.hasClass(ev.currentTarget,"theatre-control-small-btn-down")) - KHelpers.removeClass(ev.currentTarget,"theatre-control-small-btn-down"); - Theatre.instance.isDelayEmote = false; + if (KHelpers.hasClass(ev.currentTarget, "theatre-control-small-btn-down")) KHelpers.removeClass(ev.currentTarget, "theatre-control-small-btn-down"); + Theatre.instance.isDelayEmote = false; } else { - if (!KHelpers.hasClass(ev.currentTarget,"theatre-control-small-btn-down")) - KHelpers.addClass(ev.currentTarget,"theatre-control-small-btn-down"); - Theatre.instance.isDelayEmote = true; + if (!KHelpers.hasClass(ev.currentTarget, "theatre-control-small-btn-down")) KHelpers.addClass(ev.currentTarget, "theatre-control-small-btn-down"); + Theatre.instance.isDelayEmote = true; } // push focus to chat-message - let chatMessage = document.getElementById("chat-message"); - chatMessage.focus(); + let chatMessage = document.getElementById("chat-message"); + chatMessage.focus(); } - /** * Handle the Quote toggle click * * @param ev (Event) : The Event that triggered this handler */ handleBtnQuoteClick(ev) { - if (Theatre.DEBUG) console.log("quote click"); + if (Theatre.DEBUG) console.log("quote click"); if (Theatre.instance.isQuoteAuto) { - if (KHelpers.hasClass(ev.currentTarget,"theatre-control-small-btn-down")) - KHelpers.removeClass(ev.currentTarget,"theatre-control-small-btn-down"); - Theatre.instance.isQuoteAuto = false; + if (KHelpers.hasClass(ev.currentTarget, "theatre-control-small-btn-down")) KHelpers.removeClass(ev.currentTarget, "theatre-control-small-btn-down"); + Theatre.instance.isQuoteAuto = false; } else { - if (!KHelpers.hasClass(ev.currentTarget,"theatre-control-small-btn-down")) - KHelpers.addClass(ev.currentTarget,"theatre-control-small-btn-down"); - Theatre.instance.isQuoteAuto = true; + if (!KHelpers.hasClass(ev.currentTarget, "theatre-control-small-btn-down")) KHelpers.addClass(ev.currentTarget, "theatre-control-small-btn-down"); + Theatre.instance.isQuoteAuto = true; } // push focus to chat-message - let chatMessage = document.getElementById("chat-message"); - chatMessage.focus(); + let chatMessage = document.getElementById("chat-message"); + chatMessage.focus(); } /** @@ -5783,13 +5581,12 @@ class Theatre { * @param ev (Event) : The Event that triggered this handler */ handleBtnResyncClick(ev) { - if (Theatre.DEBUG) console.log("resync click"); + if (Theatre.DEBUG) console.log("resync click"); if (game.user.isGM) { - Theatre.instance._sendResyncRequest("players"); - ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.ResyncGM")); - } - else { - Theatre.instance._sendResyncRequest("gm"); + Theatre.instance._sendResyncRequest("players"); + ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.ResyncGM")); + } else { + Theatre.instance._sendResyncRequest("gm"); } } @@ -5799,14 +5596,13 @@ class Theatre { * @param ev (Event) : The Event that triggered this handler */ handleBtnSuppressClick(ev) { - if (Theatre.DEBUG) console.log("suppression click"); + if (Theatre.DEBUG) console.log("suppression click"); if (Theatre.instance.isSuppressed) { - if (KHelpers.hasClass(ev.currentTarget,"theatre-control-btn-down")) { - KHelpers.removeClass(ev.currentTarget,"theatre-control-btn-down"); + if (KHelpers.hasClass(ev.currentTarget, "theatre-control-btn-down")) { + KHelpers.removeClass(ev.currentTarget, "theatre-control-btn-down"); } - } - else { - KHelpers.addClass(ev.currentTarget,"theatre-control-btn-down"); + } else { + KHelpers.addClass(ev.currentTarget, "theatre-control-btn-down"); } Theatre.instance.updateSuppression(!Theatre.instance.isSuppressed); } @@ -5817,16 +5613,15 @@ class Theatre { let primeBar = document.getElementById("theatre-prime-bar"); let secondBar = document.getElementById("theatre-second-bar"); if (Theatre.instance.isSuppressed) { - let combatActive = game.combats.active; - Theatre.instance.isSuppressed = true; + let combatActive = game.combats.active; + Theatre.instance.isSuppressed = true; //Theatre.instance.theatreGroup.style.opacity = (combatActive ? "0.05" : "0.20"); - Theatre.instance.theatreDock.style.opacity = (combatActive ? "0.05" : "0.20"); - Theatre.instance.theatreBar.style.opacity = (combatActive ? "0.05" : "0.20"); - Theatre.instance.theatreNarrator.style.opacity = (combatActive ? "0.05" : "0.20"); - + Theatre.instance.theatreDock.style.opacity = combatActive ? "0.05" : "0.20"; + Theatre.instance.theatreBar.style.opacity = combatActive ? "0.05" : "0.20"; + Theatre.instance.theatreNarrator.style.opacity = combatActive ? "0.05" : "0.20"; - primeBar.style["pointer-events"] = "none"; - secondBar.style["pointer-events"] = "none"; + primeBar.style["pointer-events"] = "none"; + secondBar.style["pointer-events"] = "none"; } else { //Theatre.instance.theatreGroup.style.opacity = "1"; Theatre.instance.theatreDock.style.opacity = "1"; @@ -5834,7 +5629,7 @@ class Theatre { Theatre.instance.theatreNarrator.style.opacity = "1"; primeBar.style["pointer-events"] = "all"; - secondBar.style["pointer-events"] = "all"; + secondBar.style["pointer-events"] = "all"; } // call hooks @@ -5842,15 +5637,15 @@ class Theatre { } /** - * Handle naveBar Wheel + * Handle naveBar Wheel * * @param ev (Event) : The Event that triggered this handler */ handleNavBarWheel(ev) { - ev.preventDefault(); - let pos = ev.deltaY > 0; - ev.currentTarget.scrollLeft += (pos ? 10 : -10); - //ev.currentTarget.scrollLeft -= ev.deltaY/4; + ev.preventDefault(); + let pos = ev.deltaY > 0; + ev.currentTarget.scrollLeft += pos ? 10 : -10; + //ev.currentTarget.scrollLeft -= ev.deltaY/4; } /** @@ -5859,9 +5654,9 @@ class Theatre { * @param ev (Event) : The Event that triggered this handler */ handleTextBoxMouseDoubleClick(ev) { - if (Theatre.DEBUG) console.log("MOUSE DOUBLE CLICK"); - let id = ev.currentTarget.getAttribute("imgId"); - Theatre.instance.resetInsertById(id); + if (Theatre.DEBUG) console.log("MOUSE DOUBLE CLICK"); + let id = ev.currentTarget.getAttribute("imgId"); + Theatre.instance.resetInsertById(id); } /** @@ -5871,61 +5666,61 @@ class Theatre { */ handleWindowMouseUp(ev) { // finish moving insert - if (Theatre.DEBUG) console.log("WINDOW MOUSE UP"); + if (Theatre.DEBUG) console.log("WINDOW MOUSE UP"); let x = ev.clientX || ev.pageX; - let y = ev.clientY || ev.pageY; - - let insert = Theatre.instance.dragPoint.insert - let box = Theatre.instance.dragPoint.box - let ix = Theatre.instance.dragPoint.ix; - let iy = Theatre.instance.dragPoint.iy; - let ox = Theatre.instance.dragPoint.oleft; - let oy = Theatre.instance.dragPoint.otop; - - let dx = (x-ix)+ox; - let dy = (y-iy)+oy; - - if (dx < box.minleft) dx = box.minleft; - if (dx > box.maxleft) dx = box.maxleft; - if (dy > box.maxtop) dy = box.maxtop; - if (dy < box.mintop) dy = box.mintop; - - if (Theatre.DEBUG) console.log("WINDOW MOUSE UP FINAL x: "+x+" y: "+y+" ix: "+ix+" iy: "+iy+" dx: "+dx+" dy: "+dy+" ox: "+ox+" oy: "+oy); - //port.style.left = `${dx}px`; - //port.style.top = `${dy}px`; - //insert.portraitContainer.x = dx; - //insert.portraitContainer.y = dy; + let y = ev.clientY || ev.pageY; + + let insert = Theatre.instance.dragPoint.insert; + let box = Theatre.instance.dragPoint.box; + let ix = Theatre.instance.dragPoint.ix; + let iy = Theatre.instance.dragPoint.iy; + let ox = Theatre.instance.dragPoint.oleft; + let oy = Theatre.instance.dragPoint.otop; + + let dx = x - ix + ox; + let dy = y - iy + oy; + + if (dx < box.minleft) dx = box.minleft; + if (dx > box.maxleft) dx = box.maxleft; + if (dy > box.maxtop) dy = box.maxtop; + if (dy < box.mintop) dy = box.mintop; + + if (Theatre.DEBUG) console.log("WINDOW MOUSE UP FINAL x: " + x + " y: " + y + " ix: " + ix + " iy: " + iy + " dx: " + dx + " dy: " + dy + " ox: " + ox + " oy: " + oy); + //port.style.left = `${dx}px`; + //port.style.top = `${dy}px`; + //insert.portraitContainer.x = dx; + //insert.portraitContainer.y = dy; if (!insert.dockContainer || !insert.portraitContainer) { - console.log("ERROR: insert dockContainer or portrait is INVALID"); - window.removeEventListener("mouseup",Theatre.instance.handleWindowMouseUp); - return; + console.log("ERROR: insert dockContainer or portrait is INVALID"); + window.removeEventListener("mouseup", Theatre.instance.handleWindowMouseUp); + return; } - let tweenId = "portraitMove"; - let tween = TweenMax.to(insert.portraitContainer,0.5,{ - pixi:{x: dx, y: dy}, + let tweenId = "portraitMove"; + let tween = TweenMax.to(insert.portraitContainer, 0.5, { + pixi: { x: dx, y: dy }, ease: Power3.easeOut, - onComplete: function(ctx,imgId,tweenId) { + onComplete: function (ctx, imgId, tweenId) { // decrement the rendering accumulator - ctx._removeDockTween(imgId,this,tweenId); + ctx._removeDockTween(imgId, this, tweenId); // remove our own reference from the dockContainer tweens }, - onCompleteParams: [Theatre.instance,insert.imgId,tweenId] - }); - Theatre.instance._addDockTween(insert.imgId,tween,tweenId); + onCompleteParams: [Theatre.instance, insert.imgId, tweenId], + }); + Theatre.instance._addDockTween(insert.imgId, tween, tweenId); // send sceneEvent - Theatre.instance._sendSceneEvent("positionupdate",{ - insertid : insert.imgId, - position: {x: dx, y: dy, mirror: insert.mirrored} - }); + Theatre.instance._sendSceneEvent("positionupdate", { + insertid: insert.imgId, + position: { x: dx, y: dy, mirror: insert.mirrored }, + }); - window.removeEventListener("mouseup",Theatre.instance.handleWindowMouseUp); - Theatre.instance.dragPoint = null; + window.removeEventListener("mouseup", Theatre.instance.handleWindowMouseUp); + Theatre.instance.dragPoint = null; // push focus to chat-message - let chatMessage = document.getElementById("chat-message"); - chatMessage.focus(); + let chatMessage = document.getElementById("chat-message"); + chatMessage.focus(); } /** @@ -5934,64 +5729,62 @@ class Theatre { * @param ev (Event) : The Event that triggered this handler */ handleTextBoxMouseDown(ev) { - if (Theatre.DEBUG) console.log("MOUSE DOWN ",ev.buttons, ev.button); - let id = ev.currentTarget.getAttribute("imgId"); + if (Theatre.DEBUG) console.log("MOUSE DOWN ", ev.buttons, ev.button); + let id = ev.currentTarget.getAttribute("imgId"); if (ev.button == 0) { - if (!ev.ctrlKey - && !ev.shiftKey - && !ev.altKey) { + if (!ev.ctrlKey && !ev.shiftKey && !ev.altKey) { // if old dragPoint exists reset the style, and clear any interval that may exist if (!!Theatre.instance.dragPoint && !!Theatre.instance.dragPoint.insert) { - console.log("PREXISTING DRAGPOINT!"); - //Theatre.instance.dragPoint.port.style.transition = "top 0.5s ease, left 0.5s ease, transform 0.5s ease"; + console.log("PREXISTING DRAGPOINT!"); + //Theatre.instance.dragPoint.port.style.transition = "top 0.5s ease, left 0.5s ease, transform 0.5s ease"; } // calculate bouding box - let boundingBox = {}; - let insert = Theatre.instance.getInsertById(id); + let boundingBox = {}; + let insert = Theatre.instance.getInsertById(id); // permission check - if (!Theatre.instance.isActorOwner(game.user.id,insert.imgId)) { + if (!Theatre.instance.isActorOwner(game.user.id, insert.imgId)) { ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.DoNotControl")); - return; + return; } // max top is half natural height // min top is zero to prevent it from losing it's flush // max left is half natural width // min left is - half natural width - boundingBox["maxtop"] = (insert.optAlign == "top" ? 0 : insert.portrait.height); - boundingBox["mintop"] = insert.portrait.height / 2; - boundingBox["maxleft"] = insert.portrait.width * 3 / 2; - boundingBox["minleft"] = 0; + boundingBox["maxtop"] = insert.optAlign == "top" ? 0 : insert.portrait.height; + boundingBox["mintop"] = insert.portrait.height / 2; + boundingBox["maxleft"] = (insert.portrait.width * 3) / 2; + boundingBox["minleft"] = 0; // original cooords - //let portStyles = KHelpers.style(port); - let origX = insert.portraitContainer.x; - let origY = insert.portraitContainer.y; + //let portStyles = KHelpers.style(port); + let origX = insert.portraitContainer.x; + let origY = insert.portraitContainer.y; - if (Theatre.DEBUG) console.log("STORING DRAG POINT",ev.clientX || ev.pageX, ev.clientY || ev.PageY, boundingBox, origX, origY); + if (Theatre.DEBUG) console.log("STORING DRAG POINT", ev.clientX || ev.pageX, ev.clientY || ev.PageY, boundingBox, origX, origY); // change the transition style while we're dragging - //port.style.transition = "top 0.5s ease, left 0.5s ease, transform 0.5s ease"; + //port.style.transition = "top 0.5s ease, left 0.5s ease, transform 0.5s ease"; // normal mouse down, start "drag" tracking Theatre.instance.dragPoint = { otop: origY, - oleft: origX, - ix: (ev.clientX || ev.pageX), - iy: (ev.clientY || ev.pageY), + oleft: origX, + ix: ev.clientX || ev.pageX, + iy: ev.clientY || ev.pageY, insert: insert, box: boundingBox, - } + }; // bind listeners - window.removeEventListener("mouseup",Theatre.instance.handleWindowMouseUp); - window.addEventListener("mouseup",Theatre.instance.handleWindowMouseUp); - ev.stopPropagation(); + window.removeEventListener("mouseup", Theatre.instance.handleWindowMouseUp); + window.addEventListener("mouseup", Theatre.instance.handleWindowMouseUp); + ev.stopPropagation(); } } else if (ev.button == 2) { - Theatre.instance.swapTarget = id; - ev.stopPropagation(); + Theatre.instance.swapTarget = id; + ev.stopPropagation(); } } @@ -6001,51 +5794,50 @@ class Theatre { * @param ev (Event) : The Event that triggered this handler */ handleTextBoxMouseUp(ev) { - if (Theatre.DEBUG) console.log("MOUSE UP ",ev.buttons, ev.button); - let id = ev.currentTarget.getAttribute("imgId"); - let chatMessage = document.getElementById("chat-message"); + if (Theatre.DEBUG) console.log("MOUSE UP ", ev.buttons, ev.button); + let id = ev.currentTarget.getAttribute("imgId"); + let chatMessage = document.getElementById("chat-message"); if (ev.button == 0) { if (ev.ctrlKey) { - Theatre.instance.decayTextBoxById(id); - ev.stopPropagation(); + Theatre.instance.decayTextBoxById(id); + ev.stopPropagation(); } else if (ev.shiftKey) { - Theatre.instance.pushInsertById(id,true); - chatMessage.focus(); - ev.stopPropagation(); + Theatre.instance.pushInsertById(id, true); + chatMessage.focus(); + ev.stopPropagation(); } else if (ev.altKey) { // activate navitem // activate insert - Theatre.instance.activateInsertById(id,ev); + Theatre.instance.activateInsertById(id, ev); } } else if (ev.button == 2) { if (ev.ctrlKey) { - Theatre.instance.removeInsertById(id); - ev.stopPropagation(); + Theatre.instance.removeInsertById(id); + ev.stopPropagation(); } else if (ev.shiftKey) { - if (Theatre.instance.swapTarget - && Theatre.instance.swapTarget != id) { - Theatre.instance.swapInsertsById(id,Theatre.instance.swapTarget); - Theatre.instance.swapTarget = null; + if (Theatre.instance.swapTarget && Theatre.instance.swapTarget != id) { + Theatre.instance.swapInsertsById(id, Theatre.instance.swapTarget); + Theatre.instance.swapTarget = null; } else { - Theatre.instance.pushInsertById(id,false); + Theatre.instance.pushInsertById(id, false); } - chatMessage.focus(); - ev.stopPropagation(); + chatMessage.focus(); + ev.stopPropagation(); } else if (ev.altKey) { - let actor = game.actors.get(id.replace("theatre-","")); - Theatre.addToNavBar(actor.data); + let actor = game.actors.get(id.replace("theatre-", "")); + Theatre.addToNavBar(actor.data); } else if (Theatre.instance.swapTarget) { if (Theatre.instance.swapTarget != id) { - //Theatre.instance.swapInsertsById(id,Theatre.instance.swapTarget); - Theatre.instance.moveInsertById(id,Theatre.instance.swapTarget); - Theatre.instance.swapTarget = null; + //Theatre.instance.swapInsertsById(id,Theatre.instance.swapTarget); + Theatre.instance.moveInsertById(id, Theatre.instance.swapTarget); + Theatre.instance.swapTarget = null; } else { - Theatre.instance.mirrorInsertById(id); + Theatre.instance.mirrorInsertById(id); } - ev.stopPropagation(); - chatMessage.focus(); - Theatre.instance.swapTarget = null; - } + ev.stopPropagation(); + chatMessage.focus(); + Theatre.instance.swapTarget = null; + } } } @@ -6055,13 +5847,13 @@ class Theatre { * @param ev (Event) : The Event that triggered this handler */ handleNavItemDragStart(ev) { - //ev.preventDefault(); - ev.dataTransfer.clearData("text/plain"); - ev.dataTransfer.clearData("text/html"); - ev.dataTransfer.clearData("text/uri-list"); - ev.dataTransfer.dropEffect = "move"; - ev.dataTransfer.setDragImage(ev.currentTarget,16,16); - Theatre.instance.dragNavItem = ev.currentTarget; + //ev.preventDefault(); + ev.dataTransfer.clearData("text/plain"); + ev.dataTransfer.clearData("text/html"); + ev.dataTransfer.clearData("text/uri-list"); + ev.dataTransfer.dropEffect = "move"; + ev.dataTransfer.setDragImage(ev.currentTarget, 16, 16); + Theatre.instance.dragNavItem = ev.currentTarget; } /** @@ -6070,8 +5862,8 @@ class Theatre { * @param ev (Event) : The Event that triggered this handler */ handleNavItemDragEnd(ev) { - ev.preventDefault(); - Theatre.instance.dragNavItem = null; + ev.preventDefault(); + Theatre.instance.dragNavItem = null; } /** @@ -6080,8 +5872,8 @@ class Theatre { * @param ev (Event) : The Event that triggered this handler */ handleNavItemDragOver(ev) { - ev.preventDefault(); - ev.dataTransfer.dropEffect = "move"; + ev.preventDefault(); + ev.dataTransfer.dropEffect = "move"; } /** @@ -6090,8 +5882,8 @@ class Theatre { * @param ev (Event) : The Event that triggered this handler */ handleNavItemDragDrop(ev) { - ev.preventDefault(); - KHelpers.insertBefore(Theatre.instance.dragNavItem,ev.currentTarget); + ev.preventDefault(); + KHelpers.insertBefore(Theatre.instance.dragNavItem, ev.currentTarget); } /** @@ -6100,55 +5892,48 @@ class Theatre { * @param ev (Event) : The Event that triggered this handler */ handleNavItemMouseUp(ev) { - let navItem = ev.currentTarget; - let id = ev.currentTarget.getAttribute("imgId"); - let actorId = id.replace("theatre-",""); - let params = Theatre.instance._getInsertParamsFromActorId(actorId); + let navItem = ev.currentTarget; + let id = ev.currentTarget.getAttribute("imgId"); + let actorId = id.replace("theatre-", ""); + let params = Theatre.instance._getInsertParamsFromActorId(actorId); if (!params) { - console.log("ERROR, actorId %s does not exist!",actorId); + console.log("ERROR, actorId %s does not exist!", actorId); // remove the nav Item - ev.currentTarget.parentNode.removeChild(ev.currentTarget); - return; + ev.currentTarget.parentNode.removeChild(ev.currentTarget); + return; } - if (Theatre.DEBUG) console.log("Button UP on nav add?",ev.button); + if (Theatre.DEBUG) console.log("Button UP on nav add?", ev.button); - switch(ev.button) { + switch (ev.button) { case 0: - Theatre.instance.activateInsertById(id,ev); + Theatre.instance.activateInsertById(id, ev); break; case 2: - let removed = Theatre.instance.removeInsertById(id); - let cimg = Theatre.instance.getTheatreCoverPortrait(); + let removed = Theatre.instance.removeInsertById(id); + let cimg = Theatre.instance.getTheatreCoverPortrait(); if (ev.ctrlKey) { // unstage the actor Theatre.instance._removeFromStage(id); - return; + return; } if (!removed) { - let src = params.src; - let name = params.name; - let optAlign = params.optalign; - let emotions; + let src = params.src; + let name = params.name; + let optAlign = params.optalign; + let emotions; // determine if to launch with actor saves or default settings - if (ev.altKey) - emotions = Theatre.instance._getInitialEmotionSetFromInsertParams(params,true); - else - emotions = Theatre.instance._getInitialEmotionSetFromInsertParams(params); + if (ev.altKey) emotions = Theatre.instance._getInitialEmotionSetFromInsertParams(params, true); + else emotions = Theatre.instance._getInitialEmotionSetFromInsertParams(params); if (!ev.shiftKey) { - if (game.user.isGM) - Theatre.instance.injectLeftPortrait(src,name,id,optAlign,emotions); - else - Theatre.instance.injectRightPortrait(src,name,id,optAlign,emotions); - } else - Theatre.instance.injectRightPortrait(src,name,id,optAlign,emotions); - + if (game.user.isGM) Theatre.instance.injectLeftPortrait(src, name, id, optAlign, emotions); + else Theatre.instance.injectRightPortrait(src, name, id, optAlign, emotions); + } else Theatre.instance.injectRightPortrait(src, name, id, optAlign, emotions); } - break; + break; } - } /** @@ -6166,428 +5951,409 @@ class Theatre { * */ static reorderInserts() { - if (!Theatre.instance) return; - let boxes = Theatre.instance._getTextBoxes(); - let containerWidth = Theatre.instance.theatreDock.offsetWidth; + if (!Theatre.instance) return; + let boxes = Theatre.instance._getTextBoxes(); + let containerWidth = Theatre.instance.theatreDock.offsetWidth; // Min 22px, max 32px, scale for all values inbetween - let fontSize = Math.floor(Math.max((Math.min(containerWidth/boxes.length,500)/500)*28,18)); - if (Theatre.DEBUG) console.log("Reorder CALCUALTED FONT SIZE: ",fontSize); + let fontSize = Math.floor(Math.max((Math.min(containerWidth / boxes.length, 500) / 500) * 28, 18)); + if (Theatre.DEBUG) console.log("Reorder CALCUALTED FONT SIZE: ", fontSize); for (let textBox of boxes) { - let theatreId = textBox.getAttribute("imgid"); - let insert = Theatre.instance.getInsertById(theatreId); - + let theatreId = textBox.getAttribute("imgid"); + let insert = Theatre.instance.getInsertById(theatreId); + if (!insert) { - Theatre.instance._removeTextBoxFromTheatreBar(textBox); - continue; + Theatre.instance._removeTextBoxFromTheatreBar(textBox); + continue; } // if somehow the containers are not setup, skip and hope the next re-order has them ready - + if (!insert.portrait || !insert.label) { - if (Theatre.DEBUG) console.log("WARN: %s : %s was not ready!",insert.name,insert.imgId); - continue; + if (Theatre.DEBUG) console.log("WARN: %s : %s was not ready!", insert.name, insert.imgId); + continue; } // if the insert/textBox pair is in the process of being removed. - if (textBox.getAttribute("deleting")) - continue; + if (textBox.getAttribute("deleting")) continue; - //console.log("repositioning %s :",theatreId,insert); - let offset = KHelpers.offset(textBox); + //console.log("repositioning %s :",theatreId,insert); + let offset = KHelpers.offset(textBox); //left calc let leftPos = Math.round( - Number(offset.left || 0) - - Number(KHelpers.style(textBox)["left"].match(/\-*\d+\.*\d*/) || 0) - - Number(KHelpers.style(Theatre.instance.theatreBar)["margin-left"].match(/\-*\d+\.*\d*/) || 0) - ); + Number(offset.left || 0) - + Number(KHelpers.style(textBox)["left"].match(/\-*\d+\.*\d*/) || 0) - + Number(KHelpers.style(Theatre.instance.theatreBar)["margin-left"].match(/\-*\d+\.*\d*/) || 0) + ); - //insert.dockContainer.width = textBox.offsetWidth; + //insert.dockContainer.width = textBox.offsetWidth; if (insert.exitOrientation == "left") { - if (Theatre.DEBUG) console.log("LEFT (name: %s): ",insert.nameOrientation,leftPos,insert.name, Theatre.instance.theatreBar.offsetWidth/2); - if (leftPos+(insert.dockContainer.width/2) > Theatre.instance.theatreBar.offsetWidth/2) { - if (Theatre.DEBUG) console.log("swapping " + insert.name + " to right alignment from left"); - insert.exitOrientation = "right"; + if (Theatre.DEBUG) console.log("LEFT (name: %s): ", insert.nameOrientation, leftPos, insert.name, Theatre.instance.theatreBar.offsetWidth / 2); + if (leftPos + insert.dockContainer.width / 2 > Theatre.instance.theatreBar.offsetWidth / 2) { + if (Theatre.DEBUG) console.log("swapping " + insert.name + " to right alignment from left"); + insert.exitOrientation = "right"; } } else { - if (Theatre.DEBUG) console.log("RIGHT (name: %s): ",insert.nameOrientation,leftPos,insert.name, Theatre.instance.theatreBar.offsetWidth/2); + if (Theatre.DEBUG) console.log("RIGHT (name: %s): ", insert.nameOrientation, leftPos, insert.name, Theatre.instance.theatreBar.offsetWidth / 2); //right - if (leftPos+(insert.dockContainer.width/2) <= Theatre.instance.theatreBar.offsetWidth/2) { - if (Theatre.DEBUG) console.log("swapping " + insert.name + " to left alignment from right"); - insert.exitOrientation = "left"; + if (leftPos + insert.dockContainer.width / 2 <= Theatre.instance.theatreBar.offsetWidth / 2) { + if (Theatre.DEBUG) console.log("swapping " + insert.name + " to left alignment from right"); + insert.exitOrientation = "left"; } } // pre-split measurement - insert.label.style.fontSize = game.settings.get(Theatre.SETTINGS,"nameFontSize"); - insert.label.style.lineHeight = game.settings.get(Theatre.SETTINGS,"nameFontSize")*1.5; - insert.label.style.wordWrap = false; - insert.label.style.wordWrapWidth = insert.portrait.width; - let labelExceeds = (insert.label.width+20+insert.label.style.fontSize) > textBox.offsetWidth; - let preLabelWidth = insert.label.width; + insert.label.style.fontSize = game.settings.get(Theatre.SETTINGS, "nameFontSize"); + insert.label.style.lineHeight = game.settings.get(Theatre.SETTINGS, "nameFontSize") * 1.5; + insert.label.style.wordWrap = false; + insert.label.style.wordWrapWidth = insert.portrait.width; + let labelExceeds = insert.label.width + 20 + insert.label.style.fontSize > textBox.offsetWidth; + let preLabelWidth = insert.label.width; // split measurement - insert.label.style.wordWrap = true; - insert.label.style.wordWrapWidth = textBox.offsetWidth; + insert.label.style.wordWrap = true; + insert.label.style.wordWrapWidth = textBox.offsetWidth; // shrink if label exceeds if (labelExceeds) { // apply title font size - let titleFontSize = Math.floor(Math.max((Math.min(containerWidth/boxes.length,600)/600)*44,28)); - insert.label.style.fontSize = titleFontSize; - insert.label.style.lineHeight = titleFontSize*1.5; + let titleFontSize = Math.floor(Math.max((Math.min(containerWidth / boxes.length, 600) / 600) * 44, 28)); + insert.label.style.fontSize = titleFontSize; + insert.label.style.lineHeight = titleFontSize * 1.5; } // Scale the name bar length and orient the portait - - if (insert.nameOrientation == "left") { - insert.label.x = 20; - insert.typingBubble.anchor.set(0.5); - insert.typingBubble.x = Math.min(preLabelWidth + 20 + insert.typingBubble.width/2, textBox.offsetWidth - insert.typingBubble.width/2); + if (insert.nameOrientation == "left") { + insert.label.x = 20; + insert.typingBubble.anchor.set(0.5); + insert.typingBubble.x = Math.min(preLabelWidth + 20 + insert.typingBubble.width / 2, textBox.offsetWidth - insert.typingBubble.width / 2); } else { if (labelExceeds) { - insert.label.x = insert.portrait.width - insert.label.width - 20; + insert.label.x = insert.portrait.width - insert.label.width - 20; if (insert.label.width - 20 > insert.portrait.width) - insert.typingBubble.x = Math.min(insert.portrait.width - insert.label.width - insert.typingBubble.texture.width/2 - 20, insert.typingBubble.width/2); - else - insert.typingBubble.x = Math.max(insert.portrait.width - insert.label.width - insert.typingBubble.texture.width/2 - 20, insert.typingBubble.width/2); + insert.typingBubble.x = Math.min(insert.portrait.width - insert.label.width - insert.typingBubble.texture.width / 2 - 20, insert.typingBubble.width / 2); + else insert.typingBubble.x = Math.max(insert.portrait.width - insert.label.width - insert.typingBubble.texture.width / 2 - 20, insert.typingBubble.width / 2); } else { - insert.label.x = insert.portrait.width - preLabelWidth - 20; + insert.label.x = insert.portrait.width - preLabelWidth - 20; if (preLabelWidth - 20 > insert.portrait.width) - insert.typingBubble.x = Math.min(insert.portrait.width - preLabelWidth - insert.typingBubble.texture.width/2 - 20, insert.typingBubble.width/2); - else - insert.typingBubble.x = Math.max(insert.portrait.width - preLabelWidth - insert.typingBubble.texture.width/2 - 20, insert.typingBubble.width/2); + insert.typingBubble.x = Math.min(insert.portrait.width - preLabelWidth - insert.typingBubble.texture.width / 2 - 20, insert.typingBubble.width / 2); + else insert.typingBubble.x = Math.max(insert.portrait.width - preLabelWidth - insert.typingBubble.texture.width / 2 - 20, insert.typingBubble.width / 2); } - insert.typingBubble.anchor.set(0.5); + insert.typingBubble.anchor.set(0.5); - leftPos += textBox.offsetWidth - insert.portrait.width; + leftPos += textBox.offsetWidth - insert.portrait.width; } - insert.typingBubble.y = insert.portrait.height - - (insert.optAlign == "top" ? 0 : Theatre.instance.theatreBar.offsetHeight) - insert.label.style.lineHeight + insert.typingBubble.height/2; + insert.typingBubble.y = + insert.portrait.height - (insert.optAlign == "top" ? 0 : Theatre.instance.theatreBar.offsetHeight) - insert.label.style.lineHeight + insert.typingBubble.height / 2; // if the label height > font-size, it word wrapped wrap, so we need to bump up the height if (labelExceeds) { - let divisor = Math.round(insert.label.height/insert.label.style.lineHeight); - insert.label.y = insert.portrait.height - - (insert.optAlign == "top" ? 0 : Theatre.instance.theatreBar.offsetHeight) - (insert.label.style.lineHeight*divisor); + let divisor = Math.round(insert.label.height / insert.label.style.lineHeight); + insert.label.y = insert.portrait.height - (insert.optAlign == "top" ? 0 : Theatre.instance.theatreBar.offsetHeight) - insert.label.style.lineHeight * divisor; } else { // normal - insert.label.y = insert.portrait.height - - (insert.optAlign == "top" ? 0 : Theatre.instance.theatreBar.offsetHeight) - insert.label.style.lineHeight; + insert.label.y = insert.portrait.height - (insert.optAlign == "top" ? 0 : Theatre.instance.theatreBar.offsetHeight) - insert.label.style.lineHeight; } - insert.typingBubble.rotation = 0.1745; - insert.dockContainer.y = Theatre.instance.theatreDock.offsetHeight - - (insert.optAlign == "top" ? Theatre.instance.theatreBar.offsetHeight : 0) - insert.portrait.height; + insert.typingBubble.rotation = 0.1745; + insert.dockContainer.y = Theatre.instance.theatreDock.offsetHeight - (insert.optAlign == "top" ? Theatre.instance.theatreBar.offsetHeight : 0) - insert.portrait.height; // theatreStyle specific adjustments switch (Theatre.instance.settings.theatreStyle) { case "lightbox": // to allow top-aligned portraits to work without a seam - insert.dockContainer.y += (insert.optAlign == "top" ? 8 : 0); - insert.label.y -= (insert.optAlign == "top" ? 8 : 0); - break; + insert.dockContainer.y += insert.optAlign == "top" ? 8 : 0; + insert.label.y -= insert.optAlign == "top" ? 8 : 0; + break; case "clearbox": - insert.dockContainer.y = Theatre.instance.theatreDock.offsetHeight - insert.portrait.height; - insert.label.y += (insert.optAlign == "top" ? 0 : Theatre.instance.theatreBar.offsetHeight) - insert.typingBubble.y += (insert.optAlign == "top" ? 0 : Theatre.instance.theatreBar.offsetHeight); - break; + insert.dockContainer.y = Theatre.instance.theatreDock.offsetHeight - insert.portrait.height; + insert.label.y += insert.optAlign == "top" ? 0 : Theatre.instance.theatreBar.offsetHeight; + insert.typingBubble.y += insert.optAlign == "top" ? 0 : Theatre.instance.theatreBar.offsetHeight; + break; case "mangabubble": - break; + break; case "textbox": - break; + break; default: - break; + break; } // Based on the number of active inserts, space, and user /desired/ font size, we'll set the font size - let insertFontSize = fontSize; - textBox.setAttribute('osize',insertFontSize); + let insertFontSize = fontSize; + textBox.setAttribute("osize", insertFontSize); switch (Number(insert.textSize)) { - case 3: - insertFontSize *= 1.5 - break; + case 3: + insertFontSize *= 1.5; + break; case 1: - insertFontSize *= 0.5 - break; + insertFontSize *= 0.5; + break; default: - break; + break; } textBox.style["font-size"] = `${insertFontSize}px`; // now apply it to all children and sub child heights if the height is different // note that we only care about growing, not shrinking to conserve a bit. - if (textBox.children[0] - && textBox.children[0].tagName.toLowerCase() != "hr" - && textBox.children[0].offsetHeight != insertFontSize) { + if (textBox.children[0] && textBox.children[0].tagName.toLowerCase() != "hr" && textBox.children[0].offsetHeight != insertFontSize) { for (let c of textBox.children) { - if (c.tagName.toLowerCase() == "hr") - continue; - for (let sc of c.children) - sc.style.height = `${insertFontSize}px`; + if (c.tagName.toLowerCase() == "hr") continue; + for (let sc of c.children) sc.style.height = `${insertFontSize}px`; c.style.height = `${insertFontSize}px`; } } // bookmark leftPos as order for sorting - insert.order = leftPos; - insert.renderOrder = leftPos; + insert.order = leftPos; + insert.renderOrder = leftPos; - let tweenId = "containerSlide"; - let tween = TweenMax.to(insert.dockContainer,1,{ + let tweenId = "containerSlide"; + let tween = TweenMax.to(insert.dockContainer, 1, { //delay: 0.5, - pixi:{x: leftPos, alpha: 1}, + pixi: { x: leftPos, alpha: 1 }, ease: Power4.easeOut, - onComplete: function(ctx,imgId,tweenId) { + onComplete: function (ctx, imgId, tweenId) { // decrement the rendering accumulator - ctx._removeDockTween(imgId,this,tweenId); + ctx._removeDockTween(imgId, this, tweenId); // remove our own reference from the dockContainer tweens }, - onCompleteParams: [Theatre.instance,insert.imgId,tweenId] - }); - Theatre.instance._addDockTween(theatreId,tween,tweenId); + onCompleteParams: [Theatre.instance, insert.imgId, tweenId], + }); + Theatre.instance._addDockTween(theatreId, tween, tweenId); } // sort the render order by left position order - Theatre.instance.portraitDocks.sort((a,b)=>{return a.order-b.order}); - + Theatre.instance.portraitDocks.sort((a, b) => { + return a.order - b.order; + }); } - - /** - * Set wither or not to display or hide theatre debug information. + * Set wither or not to display or hide theatre debug information. * * @params state (Boolean) : Boolean indicating if we should toggle debug on/off */ static setDebug(state) { if (state) { - Theatre.DEBUG = true; - for (let insert of Theatre.instance.portraitDocks) - Theatre.instance.renderInsertById(insert.imgId); + Theatre.DEBUG = true; + for (let insert of Theatre.instance.portraitDocks) Theatre.instance.renderInsertById(insert.imgId); } else { - Theatre.DEBUG = false; - for (let insert of Theatre.instance.portraitDocks) - Theatre.instance.renderInsertById(insert.imgId); + Theatre.DEBUG = false; + for (let insert of Theatre.instance.portraitDocks) Theatre.instance.renderInsertById(insert.imgId); } } /** * Verify the TweenMax ease from the animation syntax shorthand. * - * @params str (String) : the ease to verify. + * @params str (String) : the ease to verify. */ static verifyEase(str) { switch (str) { case "power1": case "power1Out": - return Power1.easeOut; - break; + return Power1.easeOut; + break; case "power1In": - return Power1.easeIn; - break; + return Power1.easeIn; + break; case "power1InOut": - return Power1.easeInOut; - break; + return Power1.easeInOut; + break; case "power2": case "power2Out": - return Power2.easeOut; - break; + return Power2.easeOut; + break; case "power2In": - return Power2.easeIn; - break; + return Power2.easeIn; + break; case "power2InOut": - return Power2.easeInOut; - break; + return Power2.easeInOut; + break; case "power3": case "power3Out": - return Power3.easeOut; - break; + return Power3.easeOut; + break; case "power3In": - return Power3.easeIn; - break; + return Power3.easeIn; + break; case "power3InOut": - return Power3.easeInOut; - break; + return Power3.easeInOut; + break; case "power4": case "power4Out": - return Power4.easeOut; - break; + return Power4.easeOut; + break; case "power4In": - return Power4.easeIn; - break; + return Power4.easeIn; + break; case "power4InOut": - return Power4.easeInOut; - break; + return Power4.easeInOut; + break; case "back": case "backOut": - return Back.easeOut; - break; + return Back.easeOut; + break; case "backIn": - return Back.easeIn; - break; + return Back.easeIn; + break; case "backInOut": - return Back.easeInOut; - break; + return Back.easeInOut; + break; case "elastic": case "elasticOut": - return Elastic.easeOut; - break; + return Elastic.easeOut; + break; case "elasticIn": - return Elastic.easeIn; - break; + return Elastic.easeIn; + break; case "elasticInOut": - return Elastic.easeInOut; - break; + return Elastic.easeInOut; + break; case "bounce": case "bounceOut": - return Bounce.easeOut; - break; + return Bounce.easeOut; + break; case "bounceIn": - return Bounce.easeIn; - break; + return Bounce.easeIn; + break; case "bounceInOut": - return Bounce.easeInOut; - break; + return Bounce.easeInOut; + break; case "circ": case "circOut": - return Circ.easeOut; - break; + return Circ.easeOut; + break; case "circIn": - return Circ.easeIn; - break; + return Circ.easeIn; + break; case "circInOut": - return Circ.easeInOut; - break; + return Circ.easeInOut; + break; case "expo": case "expoOut": - return Expo.easeOut; - break; + return Expo.easeOut; + break; case "expoIn": - return Expo.easeIn; - break; + return Expo.easeIn; + break; case "expoInOut": - return Expo.easeInOut; - break; + return Expo.easeInOut; + break; case "sine": case "sineOut": - return Sine.easeOut; - break; + return Sine.easeOut; + break; case "sineIn": - return Sine.easeIn; - break; + return Sine.easeIn; + break; case "sineInOut": - return Sine.easeInOut; - break; + return Sine.easeInOut; + break; case "power0": default: - return Power0.easeNone; - break; + return Power0.easeNone; + break; } } /** * Return an array of tween params if the syntax is correct, * else return an empty array if any tweens in the syntax - * are flag as incorrect. + * are flag as incorrect. * * @param str (String) : The syntax to verify * * @return (Array[Object]) : The array of verified tween params, or null */ static verifyAnimationSyntax(str) { - if (!str || typeof(str) != "string") return null; - if (Theatre.DEBUG) console.log("verifying syntax %s",str); - let tweenParams = []; + if (!str || typeof str != "string") return null; + if (Theatre.DEBUG) console.log("verifying syntax %s", str); + let tweenParams = []; try { - let sections = str.split('|'); - let resName = sections[0]; + let sections = str.split("|"); + let resName = sections[0]; let verifyTarget = function (target) { // TODO verify each property - return true; - } + return true; + }; - for (let sdx=1; sdx= 0; --idx) { - if (Theatre.FONTS[idx] == Theatre.instance.titleFont - || Theatre.FONTS[idx] == Theatre.instance.textFont) - continue; - oFonts.push(Theatre.FONTS[idx]); + let oFonts = []; + for (let idx = Theatre.FONTS.length - 1; idx >= 0; --idx) { + if (Theatre.FONTS[idx] == Theatre.instance.titleFont || Theatre.FONTS[idx] == Theatre.instance.textFont) continue; + oFonts.push(Theatre.FONTS[idx]); } - var aLoader = async function(fonts) { + var aLoader = async function (fonts) { WebFont.load({ custom: { - families: fonts - } - }); - } - - aLoader(oFonts); + families: fonts, + }, + }); + }; + aLoader(oFonts); } - return Theatre.FONTS; + return Theatre.FONTS; } static getActorDisplayName(actorId) { @@ -6850,30 +6613,28 @@ class Theatre { * * @param actorId (String) : The actorId of the actor to get emotes from. * @param disableDefault (Boolean) : Wither or not default emotes are disabled. - * in which case, we don't merge the actor - * emotes with the default ones. + * in which case, we don't merge the actor + * emotes with the default ones. * - * @return (Object) : An Object containg the emotes for the requested actorId. + * @return (Object) : An Object containg the emotes for the requested actorId. */ - static getActorEmotes(actorId,disableDefault) { - let actor = game.actors.get(actorId); - let data,ae,de,re; + static getActorEmotes(actorId, disableDefault) { + let actor = game.actors.get(actorId); + let data, ae, de, re; - if (actor) - data = actor.data; + if (actor) data = actor.data; if (data && data.flags.theatre) { - ae = data.flags.theatre.emotes; + ae = data.flags.theatre.emotes; if (disableDefault) { - re = ae; + re = ae; } else { - de = Theatre.getDefaultEmotes(); - re = mergeObject(de,ae); + de = Theatre.getDefaultEmotes(); + re = mergeObject(de, ae); } - } else - re = Theatre.getDefaultEmotes(); + } else re = Theatre.getDefaultEmotes(); - return re; + return re; } /** @@ -6884,728 +6645,837 @@ class Theatre { * from. * * @return (Array[(Object)]) : An array of {name: (String), path: (String)} tuples - * representing the rigging resource map for the specified actorId. + * representing the rigging resource map for the specified actorId. */ static getActorRiggingResources(actorId) { - let actor = game.actors.get(actorId); - let data,ar,dr,rr; - - if (actor) - data = actor.data; + let actor = game.actors.get(actorId); + let data, ar, dr, rr; - dr = Theatre.getDefaultRiggingResources(); - if (data - && data.flags.theatre - && data.flags.theatre.rigging - && data.flags.theatre.rigging.resources) { - ar = data.flags.theatre.rigging.resources; - rr = dr.concat(ar); - } else - rr = dr; + if (actor) data = actor.data; - return rr; + dr = Theatre.getDefaultRiggingResources(); + if (data && data.flags.theatre && data.flags.theatre.rigging && data.flags.theatre.rigging.resources) { + ar = data.flags.theatre.rigging.resources; + rr = dr.concat(ar); + } else rr = dr; + return rr; } /** * Default rigging resources * * @return (Array[(Object)]) : An array of {name: (String), path: (String)} tuples - * representing the default rigging resource map. + * representing the default rigging resource map. */ static getDefaultRiggingResources() { return [ // bubbles - {name: "angry", path: "modules/theatre/app/graphics/bubbles/angry.png"}, - {name: "frustrated", path: "modules/theatre/app/graphics/bubbles/frustrated.png"}, - {name: "annoyed", path: "modules/theatre/app/graphics/bubbles/annoyed.png"}, - {name: "hearts", path: "modules/theatre/app/graphics/bubbles/hearts.png"}, - {name: "sleeping", path: "modules/theatre/app/graphics/bubbles/sleeping.png"}, - {name: "surprised", path: "modules/theatre/app/graphics/bubbles/surprised.png"}, - {name: "confused", path: "modules/theatre/app/graphics/bubbles/confused.png"}, - {name: "awe-struck", path: "modules/theatre/app/graphics/bubbles/awe-struck.png"}, - {name: "kiss", path: "modules/theatre/app/graphics/bubbles/kiss.png"}, - {name: "blushing", path: "modules/theatre/app/graphics/bubbles/blushing.png"}, - {name: "cry", path: "modules/theatre/app/graphics/bubbles/cry.png"}, - {name: "dissatisfied", path: "modules/theatre/app/graphics/bubbles/dissatisfied.png"}, - {name: "dizzy", path: "modules/theatre/app/graphics/bubbles/dizzy.png"}, - {name: "evil", path: "modules/theatre/app/graphics/bubbles/evil.png"}, - {name: "frown", path: "modules/theatre/app/graphics/bubbles/frown.png"}, - {name: "happy", path: "modules/theatre/app/graphics/bubbles/happy.png"}, - {name: "grin", path: "modules/theatre/app/graphics/bubbles/grin.png"}, - {name: "happytears", path: "modules/theatre/app/graphics/bubbles/happytears.png"}, - {name: "laughing", path: "modules/theatre/app/graphics/bubbles/laughing.png"}, - {name: "laughingsquint", path: "modules/theatre/app/graphics/bubbles/laughingsquint.png"}, - {name: "meh", path: "modules/theatre/app/graphics/bubbles/meh.png"}, - {name: "worried", path: "modules/theatre/app/graphics/bubbles/worried.png"}, - {name: "panic", path: "modules/theatre/app/graphics/bubbles/panic.png"}, - {name: "rofl", path: "modules/theatre/app/graphics/bubbles/rofl.png"}, - {name: "sad", path: "modules/theatre/app/graphics/bubbles/sad.png"}, - {name: "scared", path: "modules/theatre/app/graphics/bubbles/scared.png"}, - {name: "smile", path: "modules/theatre/app/graphics/bubbles/smile.png"}, - {name: "playful", path: "modules/theatre/app/graphics/bubbles/playful.png"}, - {name: "smug", path: "modules/theatre/app/graphics/bubbles/smug.png"}, - {name: "tongue", path: "modules/theatre/app/graphics/bubbles/tongue.png"}, - {name: "wink", path: "modules/theatre/app/graphics/bubbles/wink.png"}, - {name: "speechless", path: "modules/theatre/app/graphics/bubbles/speechless.png"}, - {name: "thinking", path: "modules/theatre/app/graphics/bubbles/thinking.png"}, - {name: "idea", path: "modules/theatre/app/graphics/bubbles/idea.png"}, - {name: "serious", path: "modules/theatre/app/graphics/bubbles/serious.png"}, - {name: "innocent", path: "modules/theatre/app/graphics/bubbles/innocent.png"}, - {name: "carefree", path: "modules/theatre/app/graphics/bubbles/carefree.png"}, + { name: "angry", path: "modules/theatre/app/graphics/bubbles/angry.png" }, + { name: "frustrated", path: "modules/theatre/app/graphics/bubbles/frustrated.png" }, + { name: "annoyed", path: "modules/theatre/app/graphics/bubbles/annoyed.png" }, + { name: "hearts", path: "modules/theatre/app/graphics/bubbles/hearts.png" }, + { name: "sleeping", path: "modules/theatre/app/graphics/bubbles/sleeping.png" }, + { name: "surprised", path: "modules/theatre/app/graphics/bubbles/surprised.png" }, + { name: "confused", path: "modules/theatre/app/graphics/bubbles/confused.png" }, + { name: "awe-struck", path: "modules/theatre/app/graphics/bubbles/awe-struck.png" }, + { name: "kiss", path: "modules/theatre/app/graphics/bubbles/kiss.png" }, + { name: "blushing", path: "modules/theatre/app/graphics/bubbles/blushing.png" }, + { name: "cry", path: "modules/theatre/app/graphics/bubbles/cry.png" }, + { name: "dissatisfied", path: "modules/theatre/app/graphics/bubbles/dissatisfied.png" }, + { name: "dizzy", path: "modules/theatre/app/graphics/bubbles/dizzy.png" }, + { name: "evil", path: "modules/theatre/app/graphics/bubbles/evil.png" }, + { name: "frown", path: "modules/theatre/app/graphics/bubbles/frown.png" }, + { name: "happy", path: "modules/theatre/app/graphics/bubbles/happy.png" }, + { name: "grin", path: "modules/theatre/app/graphics/bubbles/grin.png" }, + { name: "happytears", path: "modules/theatre/app/graphics/bubbles/happytears.png" }, + { name: "laughing", path: "modules/theatre/app/graphics/bubbles/laughing.png" }, + { name: "laughingsquint", path: "modules/theatre/app/graphics/bubbles/laughingsquint.png" }, + { name: "meh", path: "modules/theatre/app/graphics/bubbles/meh.png" }, + { name: "worried", path: "modules/theatre/app/graphics/bubbles/worried.png" }, + { name: "panic", path: "modules/theatre/app/graphics/bubbles/panic.png" }, + { name: "rofl", path: "modules/theatre/app/graphics/bubbles/rofl.png" }, + { name: "sad", path: "modules/theatre/app/graphics/bubbles/sad.png" }, + { name: "scared", path: "modules/theatre/app/graphics/bubbles/scared.png" }, + { name: "smile", path: "modules/theatre/app/graphics/bubbles/smile.png" }, + { name: "playful", path: "modules/theatre/app/graphics/bubbles/playful.png" }, + { name: "smug", path: "modules/theatre/app/graphics/bubbles/smug.png" }, + { name: "tongue", path: "modules/theatre/app/graphics/bubbles/tongue.png" }, + { name: "wink", path: "modules/theatre/app/graphics/bubbles/wink.png" }, + { name: "speechless", path: "modules/theatre/app/graphics/bubbles/speechless.png" }, + { name: "thinking", path: "modules/theatre/app/graphics/bubbles/thinking.png" }, + { name: "idea", path: "modules/theatre/app/graphics/bubbles/idea.png" }, + { name: "serious", path: "modules/theatre/app/graphics/bubbles/serious.png" }, + { name: "innocent", path: "modules/theatre/app/graphics/bubbles/innocent.png" }, + { name: "carefree", path: "modules/theatre/app/graphics/bubbles/carefree.png" }, // effects - {name: "swirl", path: "modules/theatre/app/graphics/effects/swirl.png"}, - {name: "sweatdrop", path: "modules/theatre/app/graphics/effects/sweatdrop.png"}, - {name: "notice", path: "modules/theatre/app/graphics/effects/notice.png"}, - {name: "loud", path: "modules/theatre/app/graphics/effects/loud.png"}, - {name: "semiloud", path: "modules/theatre/app/graphics/effects/semi-loud.png"}, - {name: "veins", path: "modules/theatre/app/graphics/effects/veins.png"}, - {name: "veins_red", path: "modules/theatre/app/graphics/effects/veins_red.png"}, - {name: "twisty", path: "modules/theatre/app/graphics/effects/twisty.png"}, - {name: "glimmer", path: "modules/theatre/app/graphics/effects/glimmer.png"}, - {name: "heart", path: "modules/theatre/app/graphics/effects/heart.png"}, - {name: "puff", path: "modules/theatre/app/graphics/effects/puff.png"}, - {name: "line", path: "modules/theatre/app/graphics/effects/line.png"}, - {name: "linesteep", path: "modules/theatre/app/graphics/effects/line_steep.png"}, - {name: "star", path: "modules/theatre/app/graphics/effects/star.png"}, - {name: "musicnote", path: "modules/theatre/app/graphics/effects/musicnote.png"}, + { name: "swirl", path: "modules/theatre/app/graphics/effects/swirl.png" }, + { name: "sweatdrop", path: "modules/theatre/app/graphics/effects/sweatdrop.png" }, + { name: "notice", path: "modules/theatre/app/graphics/effects/notice.png" }, + { name: "loud", path: "modules/theatre/app/graphics/effects/loud.png" }, + { name: "semiloud", path: "modules/theatre/app/graphics/effects/semi-loud.png" }, + { name: "veins", path: "modules/theatre/app/graphics/effects/veins.png" }, + { name: "veins_red", path: "modules/theatre/app/graphics/effects/veins_red.png" }, + { name: "twisty", path: "modules/theatre/app/graphics/effects/twisty.png" }, + { name: "glimmer", path: "modules/theatre/app/graphics/effects/glimmer.png" }, + { name: "heart", path: "modules/theatre/app/graphics/effects/heart.png" }, + { name: "puff", path: "modules/theatre/app/graphics/effects/puff.png" }, + { name: "line", path: "modules/theatre/app/graphics/effects/line.png" }, + { name: "linesteep", path: "modules/theatre/app/graphics/effects/line_steep.png" }, + { name: "star", path: "modules/theatre/app/graphics/effects/star.png" }, + { name: "musicnote", path: "modules/theatre/app/graphics/effects/musicnote.png" }, //{name: "ghostball", path: "modules/theatre/app/graphics/effects/ghostball.png"}, - {name: "ghostball1", path: "modules/theatre/app/graphics/effects/ghostball1.png"}, - {name: "ghostball2", path: "modules/theatre/app/graphics/effects/ghostball2.png"}, - {name: "scribbleball", path: "modules/theatre/app/graphics/effects/scribbleball.png"}, - {name: "thoughtbubble", path: "modules/theatre/app/graphics/effects/thoughtbubble.png"}, - {name: "bubbledot", path: "modules/theatre/app/graphics/effects/bubbledot.png"}, - {name: "dot", path: "modules/theatre/app/graphics/effects/dot.png"}, - {name: "ziggy", path: "modules/theatre/app/graphics/effects/ziggy.png"}, - {name: "sinking", path: "modules/theatre/app/graphics/effects/sinking.png"}, - {name: "zzz", path: "modules/theatre/app/graphics/effects/zzz.png"}, - {name: "lightbulb", path: "modules/theatre/app/graphics/effects/lightbulb.png"}, - {name: "sigh", path: "modules/theatre/app/graphics/effects/sigh.png"}, - {name: "halo", path: "modules/theatre/app/graphics/effects/halo.png"}, - {name: "blush", path: "modules/theatre/app/graphics/effects/blush.png"}, - {name: "miasma", path: "modules/theatre/app/graphics/effects/miasma.png"}, - {name: "darkness", path: "modules/theatre/app/graphics/effects/darkness.png"}, - {name: "tears", path: "modules/theatre/app/graphics/effects/tears.png"} - ]; + { name: "ghostball1", path: "modules/theatre/app/graphics/effects/ghostball1.png" }, + { name: "ghostball2", path: "modules/theatre/app/graphics/effects/ghostball2.png" }, + { name: "scribbleball", path: "modules/theatre/app/graphics/effects/scribbleball.png" }, + { name: "thoughtbubble", path: "modules/theatre/app/graphics/effects/thoughtbubble.png" }, + { name: "bubbledot", path: "modules/theatre/app/graphics/effects/bubbledot.png" }, + { name: "dot", path: "modules/theatre/app/graphics/effects/dot.png" }, + { name: "ziggy", path: "modules/theatre/app/graphics/effects/ziggy.png" }, + { name: "sinking", path: "modules/theatre/app/graphics/effects/sinking.png" }, + { name: "zzz", path: "modules/theatre/app/graphics/effects/zzz.png" }, + { name: "lightbulb", path: "modules/theatre/app/graphics/effects/lightbulb.png" }, + { name: "sigh", path: "modules/theatre/app/graphics/effects/sigh.png" }, + { name: "halo", path: "modules/theatre/app/graphics/effects/halo.png" }, + { name: "blush", path: "modules/theatre/app/graphics/effects/blush.png" }, + { name: "miasma", path: "modules/theatre/app/graphics/effects/miasma.png" }, + { name: "darkness", path: "modules/theatre/app/graphics/effects/darkness.png" }, + { name: "tears", path: "modules/theatre/app/graphics/effects/tears.png" }, + ]; } - /** * Get default emotes, immutable * * @return (Object) : An Object, whose properties are the default set - * emotes. + * emotes. */ static getDefaultEmotes() { return { - "smile": { + smile: { name: "smile", - fatype:"far", - faname:"fa-smile", - label:game.i18n.localize("Theatre.Emote.Smile"), + fatype: "far", + faname: "fa-smile", + label: game.i18n.localize("Theatre.Emote.Smile"), rigging: { - animations: [ - {name: "smile", syntax:"smile|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"} - ] - } + animations: [{ name: "smile", syntax: "smile|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }], + }, }, - "grin": { + grin: { name: "grin", - fatype:"far", - faname:"fa-grin", - label:game.i18n.localize("Theatre.Emote.Grin"), + fatype: "far", + faname: "fa-grin", + label: game.i18n.localize("Theatre.Emote.Grin"), rigging: { - animations: [ - {name: "grin", syntax:"grin|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"} - ] - } + animations: [{ name: "grin", syntax: "grin|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }], + }, }, - "happy": { + happy: { name: "happy", - fatype:"far", - faname:"fa-smile-beam", - label:game.i18n.localize("Theatre.Emote.Happy"), + fatype: "far", + faname: "fa-smile-beam", + label: game.i18n.localize("Theatre.Emote.Happy"), rigging: { animations: [ - {name: "happy", syntax:"happy|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "line_a", syntax:"line|0.5;(ease:bounce);x:45%,40%;y:5%,0%;rotation:-20,-20"}, - {name: "line_b", syntax:"line|0.5;(ease:bounce);x:35%,25%;y:15%,12%;rotation:-65,-65"}, - {name: "line_c", syntax:"line|0.5;(ease:bounce);x:55%,60%;y:5%,0%;rotation:20,20"}, - {name: "line_d", syntax:"line|0.5;(ease:bounce);x:65%,75%;y:15%,12%;rotation:65,65"} - ] - } + { name: "happy", syntax: "happy|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "line_a", syntax: "line|0.5;(ease:bounce);x:45%,40%;y:5%,0%;rotation:-20,-20" }, + { name: "line_b", syntax: "line|0.5;(ease:bounce);x:35%,25%;y:15%,12%;rotation:-65,-65" }, + { name: "line_c", syntax: "line|0.5;(ease:bounce);x:55%,60%;y:5%,0%;rotation:20,20" }, + { name: "line_d", syntax: "line|0.5;(ease:bounce);x:65%,75%;y:15%,12%;rotation:65,65" }, + ], + }, }, - "happytears": { + happytears: { name: "happytears", - fatype:"far", - faname:"fa-grin-tears", - label:game.i18n.localize("Theatre.Emote.HappyTears"), + fatype: "far", + faname: "fa-grin-tears", + label: game.i18n.localize("Theatre.Emote.HappyTears"), rigging: { animations: [ - {name: "happytears", syntax:"happytears|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "line_a", syntax:"line|0.5;(ease:bounce);x:40%,35%;y:5%,0%;rotation:-20,-20|0.5;(repeat:-1,yoyo:true);scaleX:1,1.2;scaleY:1,1.5"}, - {name: "line_b", syntax:"line|0.5;(ease:bounce);x:30%,20%;y:15%,12%;rotation:-65,-65|0.5;(repeat:-1,yoyo:true);scaleX:1,1.2;scaleY:1,1.5"}, - {name: "line_c", syntax:"line|0.5;(ease:bounce);x:60%,65%;y:5%,0%;rotation:20,20|0.5;(repeat:-1,yoyo:true);scaleX:1,1.2;scaleY:1,1.5"}, - {name: "line_d", syntax:"line|0.5;(ease:bounce);x:70%,80%;y:15%,12%;rotation:65,65|0.5;(repeat:-1,yoyo:true);scaleX:1,1.2;scaleY:1,1.5"}, - {name: "tears_a", syntax:"tears|0.5;(repeat:-1,repeatDelay:1.7);x:60%,110%;y:25%,40%;rotation:-30,-30;alpha:0.5,0|0;scaleX:-1,-1"}, - {name: "tears_b", syntax:"tears|0.5;(repeat:-1,repeatDelay:0.8);x:40%,-10%;y:25%,40%;rotation:30,30;alpha:0.5,0"} - ] - } + { name: "happytears", syntax: "happytears|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "line_a", syntax: "line|0.5;(ease:bounce);x:40%,35%;y:5%,0%;rotation:-20,-20|0.5;(repeat:-1,yoyo:true);scaleX:1,1.2;scaleY:1,1.5" }, + { name: "line_b", syntax: "line|0.5;(ease:bounce);x:30%,20%;y:15%,12%;rotation:-65,-65|0.5;(repeat:-1,yoyo:true);scaleX:1,1.2;scaleY:1,1.5" }, + { name: "line_c", syntax: "line|0.5;(ease:bounce);x:60%,65%;y:5%,0%;rotation:20,20|0.5;(repeat:-1,yoyo:true);scaleX:1,1.2;scaleY:1,1.5" }, + { name: "line_d", syntax: "line|0.5;(ease:bounce);x:70%,80%;y:15%,12%;rotation:65,65|0.5;(repeat:-1,yoyo:true);scaleX:1,1.2;scaleY:1,1.5" }, + { name: "tears_a", syntax: "tears|0.5;(repeat:-1,repeatDelay:1.7);x:60%,110%;y:25%,40%;rotation:-30,-30;alpha:0.5,0|0;scaleX:-1,-1" }, + { name: "tears_b", syntax: "tears|0.5;(repeat:-1,repeatDelay:0.8);x:40%,-10%;y:25%,40%;rotation:30,30;alpha:0.5,0" }, + ], + }, }, - "dissatisfied": { + dissatisfied: { name: "dissatisfied", - fatype:"far", - faname:"fa-frown-open", - label:game.i18n.localize("Theatre.Emote.Dissatisfied"), + fatype: "far", + faname: "fa-frown-open", + label: game.i18n.localize("Theatre.Emote.Dissatisfied"), rigging: { - animations: [ - {name: "dissatisfied", syntax:"dissatisfied|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"} - ] - } + animations: [{ name: "dissatisfied", syntax: "dissatisfied|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }], + }, }, - "frown": { + frown: { name: "frown", - fatype:"far", - faname:"fa-frown", - label:game.i18n.localize("Theatre.Emote.Frown"), + fatype: "far", + faname: "fa-frown", + label: game.i18n.localize("Theatre.Emote.Frown"), rigging: { animations: [ - {name: "frown", syntax:"frown|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "sinking", syntax:"sinking|0.5;(ease:power2);x:50%,50%;y:-20%,15%;alpha:0,0.5"} - ] - } + { name: "frown", syntax: "frown|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "sinking", syntax: "sinking|0.5;(ease:power2);x:50%,50%;y:-20%,15%;alpha:0,0.5" }, + ], + }, }, - "sad": { + sad: { name: "sad", - fatype:"far", - faname:"fa-sad-tear", - label:game.i18n.localize("Theatre.Emote.Sad"), + fatype: "far", + faname: "fa-sad-tear", + label: game.i18n.localize("Theatre.Emote.Sad"), rigging: { animations: [ - {name: "sad", syntax:"sad|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "swirl_a", syntax:"swirl|0.5;(ease:power4);x:110%,75%;y:0%,10%;alpha:0,1|1;(repeat:-1);rotation:0,360"}, - {name: "swirl_b", syntax:"swirl|0.5;(ease:power4);x:110%,65%;y:0%,40%;alpha:0,1|1;(repeat:-1);rotation:0,360"}, - {name: "swirl_c", syntax:"swirl|0.5;(ease:power4);x:110%,90%;y:110%,50%;alpha:0,1|1;(repeat:-1);rotation:0,360"}, - {name: "swirl_d", syntax:"swirl|0.5;(ease:power4);x:110%,85%;y:110%,70%;alpha:0,1|1;(repeat:-1);rotation:0,360"}, - {name: "swirl_e", syntax:"swirl|0.5;(ease:power4);x:-10%,25%;y:0%,15%;alpha:0,1|1;(repeat:-1);rotation:0,360"}, - {name: "swirl_f", syntax:"swirl|0.5;(ease:power4);x:-10%,15%;y:0%,38%;alpha:0,1|1;(repeat:-1);rotation:0,360"}, - {name: "swirl_g", syntax:"swirl|0.5;(ease:power4);x:-10%,20%;y:110%,55%;alpha:0,1|1;(repeat:-1);rotation:0,360"}, - {name: "swirl_h", syntax:"swirl|0.5;(ease:power4);x:-10%,35%;y:110%,67%;alpha:0,1|1;(repeat:-1);rotation:0,360"}, - {name: "swirl_i", syntax:"swirl|0.5;(ease:power4);x:-10%,10%;y:110%,85%;alpha:0,1|1;(repeat:-1);rotation:0,360"}, - {name: "swirl_j", syntax:"swirl|0.5;(ease:power4);x:-10%,45%;y:110%,95%;alpha:0,1|1;(repeat:-1);rotation:0,360"}, - {name: "swirl_k", syntax:"swirl|0.5;(ease:power4);x:110%,95%;y:110%,90%;alpha:0,1|1;(repeat:-1);rotation:0,360"}, - {name: "swirl_l", syntax:"swirl|0.5;(ease:power4);x:110%,70%;y:110%,82%;alpha:0,1|1;(repeat:-1);rotation:0,360"} - - ] - } + { name: "sad", syntax: "sad|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "swirl_a", syntax: "swirl|0.5;(ease:power4);x:110%,75%;y:0%,10%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, + { name: "swirl_b", syntax: "swirl|0.5;(ease:power4);x:110%,65%;y:0%,40%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, + { name: "swirl_c", syntax: "swirl|0.5;(ease:power4);x:110%,90%;y:110%,50%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, + { name: "swirl_d", syntax: "swirl|0.5;(ease:power4);x:110%,85%;y:110%,70%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, + { name: "swirl_e", syntax: "swirl|0.5;(ease:power4);x:-10%,25%;y:0%,15%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, + { name: "swirl_f", syntax: "swirl|0.5;(ease:power4);x:-10%,15%;y:0%,38%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, + { name: "swirl_g", syntax: "swirl|0.5;(ease:power4);x:-10%,20%;y:110%,55%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, + { name: "swirl_h", syntax: "swirl|0.5;(ease:power4);x:-10%,35%;y:110%,67%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, + { name: "swirl_i", syntax: "swirl|0.5;(ease:power4);x:-10%,10%;y:110%,85%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, + { name: "swirl_j", syntax: "swirl|0.5;(ease:power4);x:-10%,45%;y:110%,95%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, + { name: "swirl_k", syntax: "swirl|0.5;(ease:power4);x:110%,95%;y:110%,90%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, + { name: "swirl_l", syntax: "swirl|0.5;(ease:power4);x:110%,70%;y:110%,82%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, + ], + }, }, - "cry": { + cry: { name: "cry", - fatype:"far", - faname:"fa-sad-cry", - label:game.i18n.localize("Theatre.Emote.Cry"), + fatype: "far", + faname: "fa-sad-cry", + label: game.i18n.localize("Theatre.Emote.Cry"), rigging: { animations: [ - {name: "cry", syntax:"cry|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "tears_a", syntax:"tears|0.5;(repeat:-1,repeatDelay:0.7);x:60%,110%;y:25%,40%;rotation:-30,-30;alpha:0.5,0|0;scaleX:-1,-1"}, - {name: "tears_b", syntax:"tears|0.5;(repeat:-1,repeatDelay:0.3);x:40%,-10%;y:25%,40%;rotation:30,30;alpha:0.5,0"}, - {name: "tears_c", syntax:"tears|0.5;(repeat:-1,repeatDelay:0.8);x:60%,90%;y:25%,50%;rotation:-10,-10;alpha:0.5,0|0;scaleX:-1,-1"}, - {name: "tears_d", syntax:"tears|0.5;(repeat:-1,repeatDelay:1.0);x:40%,10%;y:25%,50%;rotation:10,10;alpha:0.5,0"}, - {name: "tears_e", syntax:"tears|0.5;(repeat:-1,repeatDelay:0.2);x:60%,90%;y:25%,30%;rotation:-50,-50;alpha:0.5,0|0;scaleX:-1,-1"}, - {name: "tears_f", syntax:"tears|0.5;(repeat:-1,repeatDelay:1.2);x:40%,10%;y:25%,30%;rotation:50,50;alpha:0.5,0"} - - ] - } + { name: "cry", syntax: "cry|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "tears_a", syntax: "tears|0.5;(repeat:-1,repeatDelay:0.7);x:60%,110%;y:25%,40%;rotation:-30,-30;alpha:0.5,0|0;scaleX:-1,-1" }, + { name: "tears_b", syntax: "tears|0.5;(repeat:-1,repeatDelay:0.3);x:40%,-10%;y:25%,40%;rotation:30,30;alpha:0.5,0" }, + { name: "tears_c", syntax: "tears|0.5;(repeat:-1,repeatDelay:0.8);x:60%,90%;y:25%,50%;rotation:-10,-10;alpha:0.5,0|0;scaleX:-1,-1" }, + { name: "tears_d", syntax: "tears|0.5;(repeat:-1,repeatDelay:1.0);x:40%,10%;y:25%,50%;rotation:10,10;alpha:0.5,0" }, + { name: "tears_e", syntax: "tears|0.5;(repeat:-1,repeatDelay:0.2);x:60%,90%;y:25%,30%;rotation:-50,-50;alpha:0.5,0|0;scaleX:-1,-1" }, + { name: "tears_f", syntax: "tears|0.5;(repeat:-1,repeatDelay:1.2);x:40%,10%;y:25%,30%;rotation:50,50;alpha:0.5,0" }, + ], + }, }, - "serious": { + serious: { name: "serious", - fatype:"far", - faname:"fa-meh-rolling-eyes", + fatype: "far", + faname: "fa-meh-rolling-eyes", image: "modules/theatre/app/graphics/emotes/serious.png", - label:game.i18n.localize("Theatre.Emote.Serious"), + label: game.i18n.localize("Theatre.Emote.Serious"), rigging: { - animations: [ - {name: "serious", syntax:"serious|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"} - ] - } + animations: [{ name: "serious", syntax: "serious|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }], + }, }, - "annoyed": { + annoyed: { name: "annoyed", - fatype:"far", - faname:"fa-meh-rolling-eyes", - label:game.i18n.localize("Theatre.Emote.Annoyed"), + fatype: "far", + faname: "fa-meh-rolling-eyes", + label: game.i18n.localize("Theatre.Emote.Annoyed"), rigging: { animations: [ - {name: "annoyed", syntax:"annoyed|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "ziggy", syntax:"ziggy|0;x:25%,25%;y:20%,20%|0.25;(repeat:-1,yoyo:true);rotation:-2,2"}, - {name: "ziggy_2", syntax:"ziggy|1;(repeat:-1,delay:1,repeatDelay:2);scaleX:1,2;scaleY:1,2;x:25%,25%;y:20%,20%;alpha:0.5,0|0.25;(repeat:-1,yoyo:true);rotation:0,5"} - ] - } + { name: "annoyed", syntax: "annoyed|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "ziggy", syntax: "ziggy|0;x:25%,25%;y:20%,20%|0.25;(repeat:-1,yoyo:true);rotation:-2,2" }, + { + name: "ziggy_2", + syntax: "ziggy|1;(repeat:-1,delay:1,repeatDelay:2);scaleX:1,2;scaleY:1,2;x:25%,25%;y:20%,20%;alpha:0.5,0|0.25;(repeat:-1,yoyo:true);rotation:0,5", + }, + ], + }, }, - "frustrated": { + frustrated: { name: "frustrated", - fatype:"far", - faname:"fa-meh-rolling-eyes", + fatype: "far", + faname: "fa-meh-rolling-eyes", image: "modules/theatre/app/graphics/emotes/frustrated.png", - label:game.i18n.localize("Theatre.Emote.Frustrated"), + label: game.i18n.localize("Theatre.Emote.Frustrated"), rigging: { animations: [ - {name: "frustrated", syntax:"frustrated|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "veins", syntax:"veins|0.5;x:45%,45%;y:10%,10%;alpha:0,1|1;(repeat:-1,yoyo:true,ease:bounce);scaleX:0.7,1;scaleY:0.7,1"} - ] - } + { name: "frustrated", syntax: "frustrated|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "veins", syntax: "veins|0.5;x:45%,45%;y:10%,10%;alpha:0,1|1;(repeat:-1,yoyo:true,ease:bounce);scaleX:0.7,1;scaleY:0.7,1" }, + ], + }, }, - "angry": { + angry: { name: "angry", - fatype:"far", - faname:"fa-angry", - label:game.i18n.localize("Theatre.Emote.Angry"), + fatype: "far", + faname: "fa-angry", + label: game.i18n.localize("Theatre.Emote.Angry"), rigging: { animations: [ - {name: "angry", syntax:"angry|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "veins", syntax:"veins_red|0.5;x:45%,45%;y:10%,10%;alpha:0,1|1;(repeat:-1,yoyo:true,ease:elastic);scaleX:0.5,1;scaleY:0.5,1|0.25;(repeat:-1,yoyo:true);rotation:0,10"}, - {name: "puff_a", syntax:"puff|0;x:80%,80%;y:15%,15%;rotation:0,0|1;(repeat:-1,delay:1,yoyo:true,ease:power4);scaleX:0.3,1;scaleY:0.3,1;alpha:0,0.5"}, - {name: "puff_b", syntax:"puff|0;x:20%,20%;y:15%,15%;rotation:0,0|1;(repeat:-1,delay:1.5,yoyo:true,ease:power4);scaleX:-0.3,-1;scaleY:0.3,1;alpha:0,0.5"}, - {name: "puff_c", syntax:"puff|0;x:70%,70%;y:5%,5%;rotation:330,330|1;(repeat:-1,delay:2,yoyo:true,ease:power4);scaleX:0.3,1;scaleY:0.3,1;alpha:0,0.5"}, - {name: "puff_d", syntax:"puff|0;x:30%,30%;y:5%,5%;rotation:30,30|1;(repeat:-1,delay:2.5,yoyo:true,ease:power4);scaleX:-0.3,-1;scaleY:0.3,1;alpha:0,0.5"} - ] - } + { name: "angry", syntax: "angry|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { + name: "veins", + syntax: "veins_red|0.5;x:45%,45%;y:10%,10%;alpha:0,1|1;(repeat:-1,yoyo:true,ease:elastic);scaleX:0.5,1;scaleY:0.5,1|0.25;(repeat:-1,yoyo:true);rotation:0,10", + }, + { name: "puff_a", syntax: "puff|0;x:80%,80%;y:15%,15%;rotation:0,0|1;(repeat:-1,delay:1,yoyo:true,ease:power4);scaleX:0.3,1;scaleY:0.3,1;alpha:0,0.5" }, + { name: "puff_b", syntax: "puff|0;x:20%,20%;y:15%,15%;rotation:0,0|1;(repeat:-1,delay:1.5,yoyo:true,ease:power4);scaleX:-0.3,-1;scaleY:0.3,1;alpha:0,0.5" }, + { name: "puff_c", syntax: "puff|0;x:70%,70%;y:5%,5%;rotation:330,330|1;(repeat:-1,delay:2,yoyo:true,ease:power4);scaleX:0.3,1;scaleY:0.3,1;alpha:0,0.5" }, + { name: "puff_d", syntax: "puff|0;x:30%,30%;y:5%,5%;rotation:30,30|1;(repeat:-1,delay:2.5,yoyo:true,ease:power4);scaleX:-0.3,-1;scaleY:0.3,1;alpha:0,0.5" }, + ], + }, }, - "laughing": { + laughing: { name: "laughing", - fatype:"far", - faname:"fa-laugh-beam", - label:game.i18n.localize("Theatre.Emote.Laughing"), + fatype: "far", + faname: "fa-laugh-beam", + label: game.i18n.localize("Theatre.Emote.Laughing"), rigging: { animations: [ - {name: "laughing", syntax:"laughing|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "semiloud", syntax:"semiloud|0.5;x:25%,25%;y:20%,20%;alpha:0,1|0.5;(ease:bounce);scaleX:0.1,1;scaleY:0.1,1|0.25;(repeat:-1,yoyo:true);rotation:-1,1"} - ] - } + { name: "laughing", syntax: "laughing|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { + name: "semiloud", + syntax: "semiloud|0.5;x:25%,25%;y:20%,20%;alpha:0,1|0.5;(ease:bounce);scaleX:0.1,1;scaleY:0.1,1|0.25;(repeat:-1,yoyo:true);rotation:-1,1", + }, + ], + }, }, - "laughingsquint": { + laughingsquint: { name: "laughingsquint", - fatype:"far", - faname:"fa-laugh-squint", - label:game.i18n.localize("Theatre.Emote.LaughingSquint"), + fatype: "far", + faname: "fa-laugh-squint", + label: game.i18n.localize("Theatre.Emote.LaughingSquint"), rigging: { animations: [ - {name: "laughingsquint", syntax:"laughingsquint|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "loud", syntax:"loud|0.5;x:25%,25%;y:20%,20%;alpha:0,1|0.5;(ease:bounce);scaleX:0.1,1;scaleY:0.1,1|0.125;(repeat:-1,yoyo:true);rotation:-1,1"} - ] - } + { name: "laughingsquint", syntax: "laughingsquint|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "loud", syntax: "loud|0.5;x:25%,25%;y:20%,20%;alpha:0,1|0.5;(ease:bounce);scaleX:0.1,1;scaleY:0.1,1|0.125;(repeat:-1,yoyo:true);rotation:-1,1" }, + ], + }, }, - "rofl": { + rofl: { name: "rofl", - fatype:"far", - faname:"fa-grin-squint-tears", - label:game.i18n.localize("Theatre.Emote.ROFL"), + fatype: "far", + faname: "fa-grin-squint-tears", + label: game.i18n.localize("Theatre.Emote.ROFL"), rigging: { animations: [ - {name: "rofl", syntax:"rofl|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "loud_a", syntax:"loud|0.5;(ease:bounce);x:20%,20%;y:20%,20%;scaleX:0.1,1;scaleY:0.1,1|0.125;(repeat:-1,yoyo:true);rotation:-2,2"}, - {name: "loud_b", syntax:"loud|0.5;(ease:bounce);x:80%,80%;y:20%,20%;scaleX:-0.1,-1;scaleY:0.1,1|0.125;(repeat:-1,yoyo:true);rotation:-2,2"}, - {name: "loud_c", syntax:"loud|0;x:20%,20%;y:20%,20%|0.125;(repeat:-1,yoyo:true);rotation:-2,2|1;(repeat:-1);scaleX:1,1.5;scaleY:1,2;alpha:0.25,0"}, - {name: "loud_d", syntax:"loud|0;x:80%,80%;y:20%,20%|0.125;(repeat:-1,yoyo:true);rotation:-2,2|1;(repeat:-1);scaleX:-1,-1.5;scaleY:1,2;alpha:0.25,0"}, - {name: "tears_a", syntax:"tears|0.5;(repeat:-1,repeatDelay:1.7);x:60%,110%;y:25%,40%;rotation:-30,-30;alpha:0.5,0|0;scaleX:-1,-1"}, - {name: "tears_b", syntax:"tears|0.5;(repeat:-1,repeatDelay:0.8);x:40%,-10%;y:25%,40%;rotation:30,30;alpha:0.5,0"} - ] - } + { name: "rofl", syntax: "rofl|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "loud_a", syntax: "loud|0.5;(ease:bounce);x:20%,20%;y:20%,20%;scaleX:0.1,1;scaleY:0.1,1|0.125;(repeat:-1,yoyo:true);rotation:-2,2" }, + { name: "loud_b", syntax: "loud|0.5;(ease:bounce);x:80%,80%;y:20%,20%;scaleX:-0.1,-1;scaleY:0.1,1|0.125;(repeat:-1,yoyo:true);rotation:-2,2" }, + { name: "loud_c", syntax: "loud|0;x:20%,20%;y:20%,20%|0.125;(repeat:-1,yoyo:true);rotation:-2,2|1;(repeat:-1);scaleX:1,1.5;scaleY:1,2;alpha:0.25,0" }, + { name: "loud_d", syntax: "loud|0;x:80%,80%;y:20%,20%|0.125;(repeat:-1,yoyo:true);rotation:-2,2|1;(repeat:-1);scaleX:-1,-1.5;scaleY:1,2;alpha:0.25,0" }, + { name: "tears_a", syntax: "tears|0.5;(repeat:-1,repeatDelay:1.7);x:60%,110%;y:25%,40%;rotation:-30,-30;alpha:0.5,0|0;scaleX:-1,-1" }, + { name: "tears_b", syntax: "tears|0.5;(repeat:-1,repeatDelay:0.8);x:40%,-10%;y:25%,40%;rotation:30,30;alpha:0.5,0" }, + ], + }, }, - "worried": { + worried: { name: "worried", - fatype:"far", - faname:"fa-grin-beam-sweat", - label:game.i18n.localize("Theatre.Emote.Worried"), + fatype: "far", + faname: "fa-grin-beam-sweat", + label: game.i18n.localize("Theatre.Emote.Worried"), rigging: { animations: [ - {name: "worried", syntax:"worried|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "sweatdrop", syntax:"sweatdrop|2;(ease:bounce);x:30%,30%;y:0%,25%;alpha:0,1"} - ] - } + { name: "worried", syntax: "worried|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "sweatdrop", syntax: "sweatdrop|2;(ease:bounce);x:30%,30%;y:0%,25%;alpha:0,1" }, + ], + }, }, - "surprised": { + surprised: { name: "surprised", - fatype:"far", - faname:"fa-surprise", - label:game.i18n.localize("Theatre.Emote.Surprised"), + fatype: "far", + faname: "fa-surprise", + label: game.i18n.localize("Theatre.Emote.Surprised"), rigging: { animations: [ - {name: "surprised", syntax:"surprised|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "notice", syntax:"notice|0.5;x:25%,25%;y:20%,20%;alpha:0,1|0.5;(ease:bounce);scaleX:0.1,1;scaleY:0.1,1"} - ] - } + { name: "surprised", syntax: "surprised|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "notice", syntax: "notice|0.5;x:25%,25%;y:20%,20%;alpha:0,1|0.5;(ease:bounce);scaleX:0.1,1;scaleY:0.1,1" }, + ], + }, }, "awe-struck": { name: "awe-struck", - fatype:"far", - faname:"fa-grin-stars", - label:game.i18n.localize("Theatre.Emote.Awe-Struck"), + fatype: "far", + faname: "fa-grin-stars", + label: game.i18n.localize("Theatre.Emote.Awe-Struck"), rigging: { animations: [ - {name: "awe-struck", syntax:"awe-struck|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "glimmer_a", syntax:"glimmer|0.5;x:10%,10%;y:58%,58%|0.5;(delay:0.2,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1"}, - {name: "glimmer_b", syntax:"glimmer|0.5;x:85%,85%;y:20%,20%|0.5;(delay:0.3,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1"}, - {name: "glimmer_c", syntax:"glimmer|0.5;x:40%,40%;y:45%,45%|0.5;(delay:0.5,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1"}, - {name: "glimmer_d", syntax:"glimmer|0.5;x:35%,35%;y:30%,30%|0.5;(delay:0.6,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1"}, - {name: "glimmer_e", syntax:"glimmer|0.5;x:65%,65%;y:35%,35%|0.5;(delay:0.4,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1"}, - {name: "glimmer_f", syntax:"glimmer|0.5;x:80%,80%;y:50%,50%|0.5;(delay:0.1,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1"}, - {name: "glimmer_g", syntax:"glimmer|0.5;x:16%,16%;y:81%,81%|0.5;(delay:0.8,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1"}, - {name: "glimmer_h", syntax:"glimmer|0.5;x:55%,55%;y:64%,64%|0.5;(delay:0.9,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1"}, - {name: "glimmer_i", syntax:"glimmer|0.5;x:44%,44%;y:95%,95%|0.5;(delay:0.7,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1"}, - {name: "glimmer_j", syntax:"glimmer|0.5;x:67%,67%;y:84%,84%|0.5;(delay:0.35,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1"}, - {name: "glimmer_k", syntax:"glimmer|0.5;x:44%,44%;y:70%,70%|0.5;(delay:0,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1"}, - {name: "glimmer_l", syntax:"glimmer|0.5;x:20%,20%;y:23%,23%|0.5;(delay:0.65,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1"} - ] - } + { name: "awe-struck", syntax: "awe-struck|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "glimmer_a", syntax: "glimmer|0.5;x:10%,10%;y:58%,58%|0.5;(delay:0.2,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, + { name: "glimmer_b", syntax: "glimmer|0.5;x:85%,85%;y:20%,20%|0.5;(delay:0.3,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, + { name: "glimmer_c", syntax: "glimmer|0.5;x:40%,40%;y:45%,45%|0.5;(delay:0.5,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, + { name: "glimmer_d", syntax: "glimmer|0.5;x:35%,35%;y:30%,30%|0.5;(delay:0.6,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, + { name: "glimmer_e", syntax: "glimmer|0.5;x:65%,65%;y:35%,35%|0.5;(delay:0.4,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, + { name: "glimmer_f", syntax: "glimmer|0.5;x:80%,80%;y:50%,50%|0.5;(delay:0.1,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, + { name: "glimmer_g", syntax: "glimmer|0.5;x:16%,16%;y:81%,81%|0.5;(delay:0.8,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, + { name: "glimmer_h", syntax: "glimmer|0.5;x:55%,55%;y:64%,64%|0.5;(delay:0.9,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, + { name: "glimmer_i", syntax: "glimmer|0.5;x:44%,44%;y:95%,95%|0.5;(delay:0.7,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, + { name: "glimmer_j", syntax: "glimmer|0.5;x:67%,67%;y:84%,84%|0.5;(delay:0.35,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, + { name: "glimmer_k", syntax: "glimmer|0.5;x:44%,44%;y:70%,70%|0.5;(delay:0,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, + { name: "glimmer_l", syntax: "glimmer|0.5;x:20%,20%;y:23%,23%|0.5;(delay:0.65,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, + ], + }, }, - "blushing": { + blushing: { name: "blushing", - fatype:"far", - faname:"fa-flushed", - label:game.i18n.localize("Theatre.Emote.Blushing"), + fatype: "far", + faname: "fa-flushed", + label: game.i18n.localize("Theatre.Emote.Blushing"), rigging: { animations: [ - {name: "blushing", syntax:"blushing|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "blush", syntax:"blush|0.5;x:25%,25%;y:25%,25%|2;(ease:sineInOut,repeat:-1,yoyo:true);scaleX:0.9,1;scaleY:0.9,1;alpha:0.5,1|0.5;(repeat:-1,yoyo:true);rotation:-3,3"} - ] - } + { name: "blushing", syntax: "blushing|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { + name: "blush", + syntax: "blush|0.5;x:25%,25%;y:25%,25%|2;(ease:sineInOut,repeat:-1,yoyo:true);scaleX:0.9,1;scaleY:0.9,1;alpha:0.5,1|0.5;(repeat:-1,yoyo:true);rotation:-3,3", + }, + ], + }, }, - "hearts": { + hearts: { name: "hearts", - fatype:"far", - faname:"fa-grin-hearts", - label:game.i18n.localize("Theatre.Emote.Hearts"), + fatype: "far", + faname: "fa-grin-hearts", + label: game.i18n.localize("Theatre.Emote.Hearts"), rigging: { animations: [ - {name: "hearts", syntax:"hearts|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "heart_a", syntax:"heart|2;(repeat:-1,delay:1.3);y:110%,-10%;alpha:1,0|0.5;(delay:0.1,repeat:-1,yoyo:true);x:5%,10%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1"}, - {name: "heart_b", syntax:"heart|2;(repeat:-1,delay:0.3);y:110%,-10%;alpha:1,0|0.5;(delay:0.9,repeat:-1,yoyo:true);x:5%,10%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1"}, - {name: "heart_c", syntax:"heart|2;(repeat:-1,delay:0.8);y:110%,-10%;alpha:1,0|0.5;(delay:0.2,repeat:-1,yoyo:true);x:15%,20%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1"}, - {name: "heart_d", syntax:"heart|2;(repeat:-1,delay:0.5);y:110%,-10%;alpha:1,0|0.5;(delay:0.8,repeat:-1,yoyo:true);x:25%,30%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1"}, - {name: "heart_e", syntax:"heart|2;(repeat:-1,delay:1.7);y:110%,-10%;alpha:1,0|0.5;(delay:0.3,repeat:-1,yoyo:true);x:35%,40%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1"}, - {name: "heart_f", syntax:"heart|2;(repeat:-1,delay:2);y:110%,-10%;alpha:1,0|0.5;(delay:0.7,repeat:-1,yoyo:true);x:45%,50%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1"}, - {name: "heart_g", syntax:"heart|2;(repeat:-1,delay:1.5);y:110%,-10%;alpha:1,0|0.5;(delay:0.4,repeat:-1,yoyo:true);x:55%,60%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1"}, - {name: "heart_h", syntax:"heart|2;(repeat:-1,delay:0.7);y:110%,-10%;alpha:1,0|0.5;(delay:0.6,repeat:-1,yoyo:true);x:65%,70%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1"}, - {name: "heart_i", syntax:"heart|2;(repeat:-1,delay:1.7);y:110%,-10%;alpha:1,0|0.5;(delay:0.5,repeat:-1,yoyo:true);x:75%,80%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1"}, - {name: "heart_j", syntax:"heart|2;(repeat:-1,delay:0.4);y:110%,-10%;alpha:1,0|0.5;(delay:0.35,repeat:-1,yoyo:true);x:85%,90%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1"}, - {name: "heart_k", syntax:"heart|2;(repeat:-1,delay:2.3);y:110%,-10%;alpha:1,0|0.5;(delay:0.25,repeat:-1,yoyo:true);x:95%,100%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1"} - - ] - } + { name: "hearts", syntax: "hearts|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { + name: "heart_a", + syntax: "heart|2;(repeat:-1,delay:1.3);y:110%,-10%;alpha:1,0|0.5;(delay:0.1,repeat:-1,yoyo:true);x:5%,10%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1", + }, + { + name: "heart_b", + syntax: "heart|2;(repeat:-1,delay:0.3);y:110%,-10%;alpha:1,0|0.5;(delay:0.9,repeat:-1,yoyo:true);x:5%,10%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1", + }, + { + name: "heart_c", + syntax: "heart|2;(repeat:-1,delay:0.8);y:110%,-10%;alpha:1,0|0.5;(delay:0.2,repeat:-1,yoyo:true);x:15%,20%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1", + }, + { + name: "heart_d", + syntax: "heart|2;(repeat:-1,delay:0.5);y:110%,-10%;alpha:1,0|0.5;(delay:0.8,repeat:-1,yoyo:true);x:25%,30%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1", + }, + { + name: "heart_e", + syntax: "heart|2;(repeat:-1,delay:1.7);y:110%,-10%;alpha:1,0|0.5;(delay:0.3,repeat:-1,yoyo:true);x:35%,40%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1", + }, + { + name: "heart_f", + syntax: "heart|2;(repeat:-1,delay:2);y:110%,-10%;alpha:1,0|0.5;(delay:0.7,repeat:-1,yoyo:true);x:45%,50%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1", + }, + { + name: "heart_g", + syntax: "heart|2;(repeat:-1,delay:1.5);y:110%,-10%;alpha:1,0|0.5;(delay:0.4,repeat:-1,yoyo:true);x:55%,60%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1", + }, + { + name: "heart_h", + syntax: "heart|2;(repeat:-1,delay:0.7);y:110%,-10%;alpha:1,0|0.5;(delay:0.6,repeat:-1,yoyo:true);x:65%,70%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1", + }, + { + name: "heart_i", + syntax: "heart|2;(repeat:-1,delay:1.7);y:110%,-10%;alpha:1,0|0.5;(delay:0.5,repeat:-1,yoyo:true);x:75%,80%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1", + }, + { + name: "heart_j", + syntax: "heart|2;(repeat:-1,delay:0.4);y:110%,-10%;alpha:1,0|0.5;(delay:0.35,repeat:-1,yoyo:true);x:85%,90%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1", + }, + { + name: "heart_k", + syntax: "heart|2;(repeat:-1,delay:2.3);y:110%,-10%;alpha:1,0|0.5;(delay:0.25,repeat:-1,yoyo:true);x:95%,100%|0.25;(delay:0.2,repeat:-1,yoyo:true,ease:bounce);scaleX:0.8,1;scaleY:0.8,1", + }, + ], + }, }, - "kiss": { + kiss: { name: "kiss", - fatype:"far", - faname:"fa-kiss-wink-heart", - label:game.i18n.localize("Theatre.Emote.Kiss"), + fatype: "far", + faname: "fa-kiss-wink-heart", + label: game.i18n.localize("Theatre.Emote.Kiss"), rigging: { animations: [ - {name: "kiss", syntax:"kiss|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "blowkiss", syntax:"heart|4;(ease:expo);x:45%,-10%;alpha:1,0|0.25;(repeat:6,yoyo:true);y:25%,30%|0.25;(repeat:6,yoyo:true,ease:power4);scaleX:0.8,1.5;scaleY:0.8,1.5"} - ] - } + { name: "kiss", syntax: "kiss|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { + name: "blowkiss", + syntax: "heart|4;(ease:expo);x:45%,-10%;alpha:1,0|0.25;(repeat:6,yoyo:true);y:25%,30%|0.25;(repeat:6,yoyo:true,ease:power4);scaleX:0.8,1.5;scaleY:0.8,1.5", + }, + ], + }, }, - "thinking": { + thinking: { name: "thinking", - fatype:"far", - faname:"fa-blank", + fatype: "far", + faname: "fa-blank", image: "modules/theatre/app/graphics/emotes/thinking.png", - label:game.i18n.localize("Theatre.Emote.Thinking"), + label: game.i18n.localize("Theatre.Emote.Thinking"), rigging: { animations: [ - {name: "thinking", syntax:"thinking|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "thoughtbubble", syntax:"thoughtbubble|0.5;(ease:power3);x:25%,25%;y:10%,10%;alpha:0,1|0.5;(repeat:-1,yoyo:true);scaleX:0.95,1;scaleY:0.95,1"}, - {name: "bubbledot_a", syntax:"bubbledot|0.5;(ease:power3);x:28%,28%;y:18%,18%;alpha:0,1|1;(repeat:-1,yoyo:true,repeatDelay:0.3);scaleX:0.5,1;scaleY:0.5,1|5;(repeat:-1);rotation:0,360"}, - {name: "bubbledot_b", syntax:"bubbledot|0.5;(ease:power3);x:31%,31%;y:21%,21%;alpha:0,1|1;(repeat:-1,yoyo:true,repeatDelay:0.1);scaleX:0.5,1;scaleY:0.5,1|5;(repeat:-1);rotation:0,360"}, - {name: "bubbledot_c", syntax:"bubbledot|0.5;(ease:power3);x:34%,34%;y:24%,24%;alpha:0,1|1;(repeat:-1,yoyo:true,repeatDelay:0.5);scaleX:0.5,1;scaleY:0.5,1|5;(repeat:-1);rotation:0,360"}, - ] - } + { name: "thinking", syntax: "thinking|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "thoughtbubble", syntax: "thoughtbubble|0.5;(ease:power3);x:25%,25%;y:10%,10%;alpha:0,1|0.5;(repeat:-1,yoyo:true);scaleX:0.95,1;scaleY:0.95,1" }, + { + name: "bubbledot_a", + syntax: "bubbledot|0.5;(ease:power3);x:28%,28%;y:18%,18%;alpha:0,1|1;(repeat:-1,yoyo:true,repeatDelay:0.3);scaleX:0.5,1;scaleY:0.5,1|5;(repeat:-1);rotation:0,360", + }, + { + name: "bubbledot_b", + syntax: "bubbledot|0.5;(ease:power3);x:31%,31%;y:21%,21%;alpha:0,1|1;(repeat:-1,yoyo:true,repeatDelay:0.1);scaleX:0.5,1;scaleY:0.5,1|5;(repeat:-1);rotation:0,360", + }, + { + name: "bubbledot_c", + syntax: "bubbledot|0.5;(ease:power3);x:34%,34%;y:24%,24%;alpha:0,1|1;(repeat:-1,yoyo:true,repeatDelay:0.5);scaleX:0.5,1;scaleY:0.5,1|5;(repeat:-1);rotation:0,360", + }, + ], + }, }, - "confused": { + confused: { name: "confused", - fatype:"far", - faname:"fa-question-circle", + fatype: "far", + faname: "fa-question-circle", image: "modules/theatre/app/graphics/emotes/confused.png", - label:game.i18n.localize("Theatre.Emote.Confused"), + label: game.i18n.localize("Theatre.Emote.Confused"), rigging: { animations: [ - {name: "confused", syntax:"confused|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "scribbleball", syntax:"scribbleball|0.5;(ease:bounce);scaleX:0.1,1;scaleY:0.1,1;x:45%,45%;y:0%,0%;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:0,5"} - ] - } + { name: "confused", syntax: "confused|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { + name: "scribbleball", + syntax: "scribbleball|0.5;(ease:bounce);scaleX:0.1,1;scaleY:0.1,1;x:45%,45%;y:0%,0%;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:0,5", + }, + ], + }, }, - "idea": { + idea: { name: "idea", - fatype:"far", - faname:"fa-lightbulb", + fatype: "far", + faname: "fa-lightbulb", image: "modules/theatre/app/graphics/emotes/idea.png", - label:game.i18n.localize("Theatre.Emote.Idea"), + label: game.i18n.localize("Theatre.Emote.Idea"), rigging: { animations: [ - {name: "idea", syntax:"idea|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "lightbulb", syntax:"lightbulb|0.5;(ease:bounce);x:50%,50%;y:-10%,-10%;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:0,5|1;(repeat:-1,yoyo:true);scaleX:1,1.3;scaleY:1,1.3"} - ] - } + { name: "idea", syntax: "idea|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { + name: "lightbulb", + syntax: "lightbulb|0.5;(ease:bounce);x:50%,50%;y:-10%,-10%;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:0,5|1;(repeat:-1,yoyo:true);scaleX:1,1.3;scaleY:1,1.3", + }, + ], + }, }, - "meh": { + meh: { name: "meh", - fatype:"far", - faname:"fa-meh", - label:game.i18n.localize("Theatre.Emote.Meh"), + fatype: "far", + faname: "fa-meh", + label: game.i18n.localize("Theatre.Emote.Meh"), rigging: { animations: [ - {name: "meh", syntax:"meh|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "sigh", syntax:"sigh|3;(ease:power2);x:30%,10%;y:25%,45%;alpha:1,0;rotation:225,225;scaleX:1,1.5;scaleY:1,1.5"} - ] - } + { name: "meh", syntax: "meh|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "sigh", syntax: "sigh|3;(ease:power2);x:30%,10%;y:25%,45%;alpha:1,0;rotation:225,225;scaleX:1,1.5;scaleY:1,1.5" }, + ], + }, }, - "smug": { + smug: { name: "smug", - fatype:"far", - faname:"fa-grin-tongue-wink", + fatype: "far", + faname: "fa-grin-tongue-wink", image: "modules/theatre/app/graphics/emotes/smug.png", - label:game.i18n.localize("Theatre.Emote.Smug"), + label: game.i18n.localize("Theatre.Emote.Smug"), rigging: { - animations: [ - {name: "smug", syntax:"smug|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"} - ] - } + animations: [{ name: "smug", syntax: "smug|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }], + }, }, - "wink": { + wink: { name: "wink", - fatype:"far", - faname:"fa-grin-wink", - label:game.i18n.localize("Theatre.Emote.Wink"), + fatype: "far", + faname: "fa-grin-wink", + label: game.i18n.localize("Theatre.Emote.Wink"), rigging: { animations: [ - {name: "wink", syntax:"wink|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "kawaii_a", syntax:"star|4;(ease:expo);x:45%,-10%;y:25%,25%;alpha:1,0|2;(repeat:4);rotation:0,360"}, - {name: "kawaii_b", syntax:"star|3;(ease:expo);x:45%,10%;y:25%,12%;alpha:1,0|2;(repeat:4);rotation:0,360"}, - {name: "kawaii_c", syntax:"star|3;(ease:expo);x:45%,10%;y:25%,38%;alpha:1,0|2;(repeat:4);rotation:0,360"} - ] - } + { name: "wink", syntax: "wink|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "kawaii_a", syntax: "star|4;(ease:expo);x:45%,-10%;y:25%,25%;alpha:1,0|2;(repeat:4);rotation:0,360" }, + { name: "kawaii_b", syntax: "star|3;(ease:expo);x:45%,10%;y:25%,12%;alpha:1,0|2;(repeat:4);rotation:0,360" }, + { name: "kawaii_c", syntax: "star|3;(ease:expo);x:45%,10%;y:25%,38%;alpha:1,0|2;(repeat:4);rotation:0,360" }, + ], + }, }, - "tongue": { + tongue: { name: "tongue", - fatype:"far", - faname:"fa-grin-tongue", - label:game.i18n.localize("Theatre.Emote.Tongue"), + fatype: "far", + faname: "fa-grin-tongue", + label: game.i18n.localize("Theatre.Emote.Tongue"), rigging: { animations: [ - {name: "tongue", syntax:"tongue|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "kawaii", syntax:"star|4;(ease:expo,delay:2);x:30%,30%;y:25%,25%;alpha:1,0;scaleX:1.3,0.1;scaleY:1.3,0.1|2;(repeat:4);rotation:0,360"} - ] - } + { name: "tongue", syntax: "tongue|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "kawaii", syntax: "star|4;(ease:expo,delay:2);x:30%,30%;y:25%,25%;alpha:1,0;scaleX:1.3,0.1;scaleY:1.3,0.1|2;(repeat:4);rotation:0,360" }, + ], + }, }, - "playful": { + playful: { name: "playful", - fatype:"far", - faname:"fa-grin-tongue-wink", - label:game.i18n.localize("Theatre.Emote.Playful"), + fatype: "far", + faname: "fa-grin-tongue-wink", + label: game.i18n.localize("Theatre.Emote.Playful"), rigging: { animations: [ - {name: "playful", syntax:"playful|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "kawaii_a", syntax:"star|3;(ease:expo);x:40%,-10%;y:25%,-15%;alpha:1,0|2;(repeat:4);rotation:0,360"}, - {name: "kawaii_b", syntax:"star|4;(ease:expo);x:40%,-40%;y:25%,30%;alpha:1,0|2;(repeat:4);rotation:0,360"}, - {name: "kawaii_c", syntax:"star|3;(ease:expo);x:40%,-10%;y:25%,55%;alpha:1,0|2;(repeat:4);rotation:0,360"}, - {name: "kawaii_d", syntax:"star|3;(ease:expo);x:60%,110%;y:25%,-15%;alpha:1,0|2;(repeat:4);rotation:0,360"}, - {name: "kawaii_e", syntax:"star|4;(ease:expo);x:60%,140%;y:25%,30%;alpha:1,0|2;(repeat:4);rotation:0,360"}, - {name: "kawaii_f", syntax:"star|3;(ease:expo);x:60%,110%;y:25%,55%;alpha:1,0|2;(repeat:4);rotation:0,360"}, - {name: "kawaii_g", syntax:"star|4;(ease:expo);x:50%,50%;y:15%,-35%;alpha:1,0|2;(repeat:4);rotation:0,360"}, - {name: "kawaii_h", syntax:"star|4;(ease:expo);x:50%,50%;y:35%,85%;alpha:1,0|2;(repeat:4);rotation:0,360"} - ] - } + { name: "playful", syntax: "playful|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "kawaii_a", syntax: "star|3;(ease:expo);x:40%,-10%;y:25%,-15%;alpha:1,0|2;(repeat:4);rotation:0,360" }, + { name: "kawaii_b", syntax: "star|4;(ease:expo);x:40%,-40%;y:25%,30%;alpha:1,0|2;(repeat:4);rotation:0,360" }, + { name: "kawaii_c", syntax: "star|3;(ease:expo);x:40%,-10%;y:25%,55%;alpha:1,0|2;(repeat:4);rotation:0,360" }, + { name: "kawaii_d", syntax: "star|3;(ease:expo);x:60%,110%;y:25%,-15%;alpha:1,0|2;(repeat:4);rotation:0,360" }, + { name: "kawaii_e", syntax: "star|4;(ease:expo);x:60%,140%;y:25%,30%;alpha:1,0|2;(repeat:4);rotation:0,360" }, + { name: "kawaii_f", syntax: "star|3;(ease:expo);x:60%,110%;y:25%,55%;alpha:1,0|2;(repeat:4);rotation:0,360" }, + { name: "kawaii_g", syntax: "star|4;(ease:expo);x:50%,50%;y:15%,-35%;alpha:1,0|2;(repeat:4);rotation:0,360" }, + { name: "kawaii_h", syntax: "star|4;(ease:expo);x:50%,50%;y:35%,85%;alpha:1,0|2;(repeat:4);rotation:0,360" }, + ], + }, }, - "mischevious": { + mischevious: { name: "mischevious", - fatype:"fas", - faname:"fa-book-dead", + fatype: "fas", + faname: "fa-book-dead", image: "modules/theatre/app/graphics/emotes/evil.png", - label:game.i18n.localize("Theatre.Emote.Mischevious"), + label: game.i18n.localize("Theatre.Emote.Mischevious"), rigging: { animations: [ - {name: "evil", syntax:"evil|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "shroud", syntax:"darkness|0;x:50%,50%;y:50%,50%"}, - {name: "miasma_a", syntax:"miasma|0;x:25%,25%;y:78%,78%|3;(repeat:-1,delay:0.3);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1"}, - {name: "miasma_b", syntax:"miasma|0;x:73%,73%;y:68%,68%|3;(repeat:-1,delay:1.3);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1"}, - {name: "miasma_c", syntax:"miasma|0;x:15%,15%;y:60%,60%|3;(repeat:-1,delay:0.8);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1"}, - {name: "miasma_d", syntax:"miasma|0;x:45%,45%;y:85%,85%|3;(repeat:-1,delay:2.6);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1"}, - {name: "miasma_e", syntax:"miasma|0;x:90%,90%;y:80%,80%|3;(repeat:-1,delay:3.5);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1"}, - {name: "miasma_f", syntax:"miasma|0;x:55%,55%;y:60%,60%|3;(repeat:-1,delay:2.1);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1"}, - {name: "miasma_g", syntax:"miasma|0;x:10%,10%;y:90%,90%|3;(repeat:-1,delay:3.8);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1"}, - {name: "miasma_h", syntax:"miasma|0;x:95%,95%;y:70%,70%|3;(repeat:-1,delay:1.8);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1"}, - {name: "miasma_i", syntax:"miasma|0;x:50%,50%;y:72%,72%|3;(repeat:-1,delay:5.8);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1"}, - {name: "miasma_j", syntax:"miasma|0;x:10%,10%;y:66%,66%|3;(repeat:-1,delay:3.6);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1"}, - {name: "miasma_k", syntax:"miasma|0;x:3%,3%;y:88%,88%|3;(repeat:-1,delay:2.2);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1"}, - {name: "miasma_l", syntax:"miasma|0;x:78%,78%;y:75%,75%|3;(repeat:-1,delay:1.7);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1"}, - {name: "miasma_m", syntax:"miasma|0;x:65%,65%;y:98%,98%|3;(repeat:-1,delay:.7);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1"}, - {name: "miasma_n", syntax:"miasma|0;x:33%,33%;y:78%,78%|3;(repeat:-1,delay:4.4);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1"}, - {name: "miasma_o", syntax:"miasma|0;x:80%,80%;y:92%,92%|3;(repeat:-1,delay:5.2);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1"} - ] - } + { name: "evil", syntax: "evil|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "shroud", syntax: "darkness|0;x:50%,50%;y:50%,50%" }, + { name: "miasma_a", syntax: "miasma|0;x:25%,25%;y:78%,78%|3;(repeat:-1,delay:0.3);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, + { name: "miasma_b", syntax: "miasma|0;x:73%,73%;y:68%,68%|3;(repeat:-1,delay:1.3);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, + { name: "miasma_c", syntax: "miasma|0;x:15%,15%;y:60%,60%|3;(repeat:-1,delay:0.8);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, + { name: "miasma_d", syntax: "miasma|0;x:45%,45%;y:85%,85%|3;(repeat:-1,delay:2.6);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, + { name: "miasma_e", syntax: "miasma|0;x:90%,90%;y:80%,80%|3;(repeat:-1,delay:3.5);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, + { name: "miasma_f", syntax: "miasma|0;x:55%,55%;y:60%,60%|3;(repeat:-1,delay:2.1);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, + { name: "miasma_g", syntax: "miasma|0;x:10%,10%;y:90%,90%|3;(repeat:-1,delay:3.8);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, + { name: "miasma_h", syntax: "miasma|0;x:95%,95%;y:70%,70%|3;(repeat:-1,delay:1.8);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, + { name: "miasma_i", syntax: "miasma|0;x:50%,50%;y:72%,72%|3;(repeat:-1,delay:5.8);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, + { name: "miasma_j", syntax: "miasma|0;x:10%,10%;y:66%,66%|3;(repeat:-1,delay:3.6);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, + { name: "miasma_k", syntax: "miasma|0;x:3%,3%;y:88%,88%|3;(repeat:-1,delay:2.2);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, + { name: "miasma_l", syntax: "miasma|0;x:78%,78%;y:75%,75%|3;(repeat:-1,delay:1.7);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, + { name: "miasma_m", syntax: "miasma|0;x:65%,65%;y:98%,98%|3;(repeat:-1,delay:.7);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, + { name: "miasma_n", syntax: "miasma|0;x:33%,33%;y:78%,78%|3;(repeat:-1,delay:4.4);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, + { name: "miasma_o", syntax: "miasma|0;x:80%,80%;y:92%,92%|3;(repeat:-1,delay:5.2);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, + ], + }, }, - "innocent": { + innocent: { name: "innocent", - fatype:"fas", - faname:"fa-book-dead", + fatype: "fas", + faname: "fa-book-dead", image: "modules/theatre/app/graphics/emotes/innocent.png", - label:game.i18n.localize("Theatre.Emote.Innocent"), + label: game.i18n.localize("Theatre.Emote.Innocent"), rigging: { animations: [ - {name: "innocent", syntax:"innocent|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "halo", syntax:"halo|2;(ease:power2);x:50%,50%;alpha:0,1|2;(ease:sine,repeat:-1,yoyo:true,yoyoEase:sine);y:-3%,-5%"} - ] - } + { name: "innocent", syntax: "innocent|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "halo", syntax: "halo|2;(ease:power2);x:50%,50%;alpha:0,1|2;(ease:sine,repeat:-1,yoyo:true,yoyoEase:sine);y:-3%,-5%" }, + ], + }, }, - "carefree": { + carefree: { name: "carefree", - fatype:"fas", - faname:"fa-book-dead", + fatype: "fas", + faname: "fa-book-dead", image: "modules/theatre/app/graphics/emotes/carefree.png", - label:game.i18n.localize("Theatre.Emote.CareFree"), + label: game.i18n.localize("Theatre.Emote.CareFree"), rigging: { animations: [ - {name: "carefree", syntax:"carefree|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "musicnote_a", syntax:"musicnote|0.5;(ease:bounce);scaleX:0.1,1;scaleY:0.1,1;x:10%,10%;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-10,10|1;(ease:sine,yoyo:true,yoyoEase:sine,repeat:-1);y:20%,30%"}, - {name: "musicnote_b", syntax:"musicnote|0.5;(ease:bounce);scaleX:0.1,1;scaleY:0.1,1;x:20%,20%;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-10,10|1;(ease:sine,yoyo:true,yoyoEase:sine,repeat:-1,delay:0.25);y:15%,25%"}, - {name: "musicnote_c", syntax:"musicnote|0.5;(ease:bounce);scaleX:0.1,1;scaleY:0.1,1;x:30%,30%;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-10,10|1;(ease:sine,yoyo:true,yoyoEase:sine,repeat:-1,delay:0.5);y:20%,30%"} - ] - } + { name: "carefree", syntax: "carefree|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { + name: "musicnote_a", + syntax: "musicnote|0.5;(ease:bounce);scaleX:0.1,1;scaleY:0.1,1;x:10%,10%;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-10,10|1;(ease:sine,yoyo:true,yoyoEase:sine,repeat:-1);y:20%,30%", + }, + { + name: "musicnote_b", + syntax: "musicnote|0.5;(ease:bounce);scaleX:0.1,1;scaleY:0.1,1;x:20%,20%;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-10,10|1;(ease:sine,yoyo:true,yoyoEase:sine,repeat:-1,delay:0.25);y:15%,25%", + }, + { + name: "musicnote_c", + syntax: "musicnote|0.5;(ease:bounce);scaleX:0.1,1;scaleY:0.1,1;x:30%,30%;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-10,10|1;(ease:sine,yoyo:true,yoyoEase:sine,repeat:-1,delay:0.5);y:20%,30%", + }, + ], + }, }, - "panic": { + panic: { name: "panic", - fatype:"far", - faname:"fa-tired", - label:game.i18n.localize("Theatre.Emote.Panic"), + fatype: "far", + faname: "fa-tired", + label: game.i18n.localize("Theatre.Emote.Panic"), rigging: { animations: [ - {name: "panic", syntax:"panic|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "line_a", syntax:"linesteep|0;x:50%,50%;y:-10%,-10%|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1"}, - - {name: "line_b", syntax:"linesteep|0;x:35%,35%;y:-5%,-5%;rotation:-22.5,-22.5|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1"}, - {name: "line_c", syntax:"linesteep|0;x:15%,15%;y:5%,5%;rotation:-45,-45|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1"}, - {name: "line_d", syntax:"linesteep|0;x:0%,0%;y:20%,20%;rotation:-67.5,-67.5|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1"}, - {name: "line_e", syntax:"linesteep|0;x:-10%,-10%;y:30%,30%;rotation:-90,-90|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1"}, - - {name: "line_f", syntax:"linesteep|0;x:65%,65%;y:-5%,-5%;rotation:22.5,22.5|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1"}, - {name: "line_g", syntax:"linesteep|0;x:85%,85%;y:5%,5%;rotation:45,45|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1"}, - {name: "line_h", syntax:"linesteep|0;x:100%,100%;y:20%,20%;rotation:67.5,67.5|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1"}, - {name: "line_i", syntax:"linesteep|0;x:110%,110%;y:30%,30%;rotation:90,90|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1"} - ] - } + { name: "panic", syntax: "panic|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { name: "line_a", syntax: "linesteep|0;x:50%,50%;y:-10%,-10%|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1" }, + + { name: "line_b", syntax: "linesteep|0;x:35%,35%;y:-5%,-5%;rotation:-22.5,-22.5|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1" }, + { name: "line_c", syntax: "linesteep|0;x:15%,15%;y:5%,5%;rotation:-45,-45|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1" }, + { name: "line_d", syntax: "linesteep|0;x:0%,0%;y:20%,20%;rotation:-67.5,-67.5|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1" }, + { name: "line_e", syntax: "linesteep|0;x:-10%,-10%;y:30%,30%;rotation:-90,-90|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1" }, + + { name: "line_f", syntax: "linesteep|0;x:65%,65%;y:-5%,-5%;rotation:22.5,22.5|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1" }, + { name: "line_g", syntax: "linesteep|0;x:85%,85%;y:5%,5%;rotation:45,45|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1" }, + { name: "line_h", syntax: "linesteep|0;x:100%,100%;y:20%,20%;rotation:67.5,67.5|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1" }, + { name: "line_i", syntax: "linesteep|0;x:110%,110%;y:30%,30%;rotation:90,90|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1" }, + ], + }, }, - "dizzy": { + dizzy: { name: "dizzy", - fatype:"far", - faname:"fa-dizzy", - label:game.i18n.localize("Theatre.Emote.Dizzy"), + fatype: "far", + faname: "fa-dizzy", + label: game.i18n.localize("Theatre.Emote.Dizzy"), rigging: { animations: [ - {name: "dizzy", syntax:"dizzy|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "stars_a", syntax:"star|2;(ease:sineInOut,repeat:-1,yoyo:true);x:10%,90%;y:35%,5%|1;(repeatDelay:1,repeat:-1,yoyo:true);scaleX:0.2,1;scaleY:0.2,1;alpha:0.2,1|2;(repeat:-1);rotation:0,360"}, - {name: "stars_b", syntax:"star|2;(ease:sineInOut,repeat:-1,yoyo:true);x:90%,10%;y:5%,35%|1;(repeatDelay:1,repeat:-1,yoyo:true);scaleX:1,0.2;scaleY:1,0.2;alpha:1,0.2|2;(repeat:-1);rotation:0,360"}, - {name: "stars_c", syntax:"star|2;(ease:sineInOut,repeat:-1,yoyo:true,delay:1);x:10%,90%;y:5%,35%|1;(repeatDelay:1,delay:1,repeat:-1,yoyo:true);scaleX:0.2,1;scaleY:0.2,1;alpha:0.2,1|2;(repeat:-1);rotation:0,360"}, - {name: "stars_d", syntax:"star|2;(ease:sineInOut,repeat:-1,yoyo:true,delay:1);x:90%,10%;y:35%,5%|1;(repeatDelay:1,delay:1,repeat:-1,yoyo:true);scaleX:1,0.2;scaleY:1,0.2;alpha:1,0.2|2;(repeat:-1);rotation:0,360"} - ] - } + { name: "dizzy", syntax: "dizzy|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { + name: "stars_a", + syntax: "star|2;(ease:sineInOut,repeat:-1,yoyo:true);x:10%,90%;y:35%,5%|1;(repeatDelay:1,repeat:-1,yoyo:true);scaleX:0.2,1;scaleY:0.2,1;alpha:0.2,1|2;(repeat:-1);rotation:0,360", + }, + { + name: "stars_b", + syntax: "star|2;(ease:sineInOut,repeat:-1,yoyo:true);x:90%,10%;y:5%,35%|1;(repeatDelay:1,repeat:-1,yoyo:true);scaleX:1,0.2;scaleY:1,0.2;alpha:1,0.2|2;(repeat:-1);rotation:0,360", + }, + { + name: "stars_c", + syntax: "star|2;(ease:sineInOut,repeat:-1,yoyo:true,delay:1);x:10%,90%;y:5%,35%|1;(repeatDelay:1,delay:1,repeat:-1,yoyo:true);scaleX:0.2,1;scaleY:0.2,1;alpha:0.2,1|2;(repeat:-1);rotation:0,360", + }, + { + name: "stars_d", + syntax: "star|2;(ease:sineInOut,repeat:-1,yoyo:true,delay:1);x:90%,10%;y:35%,5%|1;(repeatDelay:1,delay:1,repeat:-1,yoyo:true);scaleX:1,0.2;scaleY:1,0.2;alpha:1,0.2|2;(repeat:-1);rotation:0,360", + }, + ], + }, }, - "speechless": { + speechless: { name: "speechless", - fatype:"far", - faname:"fa-comment-dots", + fatype: "far", + faname: "fa-comment-dots", image: "modules/theatre/app/graphics/emotes/speechless.png", - label:game.i18n.localize("Theatre.Emote.Speechless"), + label: game.i18n.localize("Theatre.Emote.Speechless"), rigging: { animations: [ - {name: "speechless", syntax:"speechless|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "dot_a", syntax:"dot|0.5;(ease:power3);x:30%,30%;y:25%,25%;alpha:0,1|1;(ease:bounce,repeat:-1,delay:0,repeatDelay:3,yoyo:true,yoyoEase:power0);scaleX:0.5,1;scaleY:0.5,1"}, - {name: "dot_b", syntax:"dot|0.5;(ease:power3);x:25%,25%;y:25%,25%;alpha:0,1|1;(ease:bounce,repeat:-1,delay:1,repeatDelay:3,yoyo:true,yoyoEase:power0);scaleX:0.5,1;scaleY:0.5,1"}, - {name: "dot_c", syntax:"dot|0.5;(ease:power3);x:20%,20%;y:25%,25%;alpha:0,1|1;(ease:bounce,repeat:-1,delay:2,repeatDelay:3,yoyo:true,yoyoEase:power0);scaleX:0.5,1;scaleY:0.5,1"} - ] - } + { name: "speechless", syntax: "speechless|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { + name: "dot_a", + syntax: "dot|0.5;(ease:power3);x:30%,30%;y:25%,25%;alpha:0,1|1;(ease:bounce,repeat:-1,delay:0,repeatDelay:3,yoyo:true,yoyoEase:power0);scaleX:0.5,1;scaleY:0.5,1", + }, + { + name: "dot_b", + syntax: "dot|0.5;(ease:power3);x:25%,25%;y:25%,25%;alpha:0,1|1;(ease:bounce,repeat:-1,delay:1,repeatDelay:3,yoyo:true,yoyoEase:power0);scaleX:0.5,1;scaleY:0.5,1", + }, + { + name: "dot_c", + syntax: "dot|0.5;(ease:power3);x:20%,20%;y:25%,25%;alpha:0,1|1;(ease:bounce,repeat:-1,delay:2,repeatDelay:3,yoyo:true,yoyoEase:power0);scaleX:0.5,1;scaleY:0.5,1", + }, + ], + }, }, - "scared": { + scared: { name: "scared", - fatype:"far", - faname:"fa-grimace", - label:game.i18n.localize("Theatre.Emote.Scared"), + fatype: "far", + faname: "fa-grimace", + label: game.i18n.localize("Theatre.Emote.Scared"), rigging: { animations: [ - {name: "scared", syntax:"scared|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "ghostball_a", syntax:"ghostball1|0;x:70%,70%|1;(ease:sine,yoyoEase:sine,repeat:-1,yoyo:true,delay:0.5);y:30%,35%;scaleX:0.8,1;scaleY:0.8,1;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-5,5"}, - {name: "ghostball_b", syntax:"ghostball1|0;x:30%,30%|1;(ease:sine,yoyoEase:sine,repeat:-1,yoyo:true,delay:1);y:10%,15%;scaleX:0.8,1;scaleY:0.8,1;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-5,5"}, - {name: "ghostball_c", syntax:"ghostball1|0;x:20%,20%|1;(ease:sine,yoyoEase:sine,repeat:-1,yoyo:true,delay:0.8);y:60%,65%;scaleX:0.8,1;scaleY:0.8,1;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-5,5"}, - {name: "ghostball_d", syntax:"ghostball2|0;x:85%,85%|1;(ease:sine,yoyoEase:sine,repeat:-1,yoyo:true,delay:0.4);y:75%,80%;scaleX:0.8,1;scaleY:0.8,1;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-5,5"}, - {name: "ghostball_e", syntax:"ghostball2|0;x:10%,10%|1;(ease:sine,yoyoEase:sine,repeat:-1,yoyo:true,delay:1.2);y:40%,45%;scaleX:0.8,1;scaleY:0.8,1;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-5,5"}, - {name: "ghostball_f", syntax:"ghostball2|0;x:60%,60%|1;(ease:sine,yoyoEase:sine,repeat:-1,yoyo:true,delay:0.6);y:80%,85%;scaleX:0.8,1;scaleY:0.8,1;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-5,5"}, - {name: "ghostball_g", syntax:"ghostball1|0;x:90%,90%|1;(ease:sine,yoyoEase:sine,repeat:-1,yoyo:true,delay:1.5);y:10%,15%;scaleX:0.8,1;scaleY:0.8,1;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-5,5"}, - {name: "ghostball_h", syntax:"ghostball2|0;x:75%,75%|1;(ease:sine,yoyoEase:sine,repeat:-1,yoyo:true,delay:0.9);y:50%,55%;scaleX:0.8,1;scaleY:0.8,1;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-5,5"} - ] - } + { name: "scared", syntax: "scared|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { + name: "ghostball_a", + syntax: "ghostball1|0;x:70%,70%|1;(ease:sine,yoyoEase:sine,repeat:-1,yoyo:true,delay:0.5);y:30%,35%;scaleX:0.8,1;scaleY:0.8,1;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-5,5", + }, + { + name: "ghostball_b", + syntax: "ghostball1|0;x:30%,30%|1;(ease:sine,yoyoEase:sine,repeat:-1,yoyo:true,delay:1);y:10%,15%;scaleX:0.8,1;scaleY:0.8,1;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-5,5", + }, + { + name: "ghostball_c", + syntax: "ghostball1|0;x:20%,20%|1;(ease:sine,yoyoEase:sine,repeat:-1,yoyo:true,delay:0.8);y:60%,65%;scaleX:0.8,1;scaleY:0.8,1;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-5,5", + }, + { + name: "ghostball_d", + syntax: "ghostball2|0;x:85%,85%|1;(ease:sine,yoyoEase:sine,repeat:-1,yoyo:true,delay:0.4);y:75%,80%;scaleX:0.8,1;scaleY:0.8,1;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-5,5", + }, + { + name: "ghostball_e", + syntax: "ghostball2|0;x:10%,10%|1;(ease:sine,yoyoEase:sine,repeat:-1,yoyo:true,delay:1.2);y:40%,45%;scaleX:0.8,1;scaleY:0.8,1;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-5,5", + }, + { + name: "ghostball_f", + syntax: "ghostball2|0;x:60%,60%|1;(ease:sine,yoyoEase:sine,repeat:-1,yoyo:true,delay:0.6);y:80%,85%;scaleX:0.8,1;scaleY:0.8,1;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-5,5", + }, + { + name: "ghostball_g", + syntax: "ghostball1|0;x:90%,90%|1;(ease:sine,yoyoEase:sine,repeat:-1,yoyo:true,delay:1.5);y:10%,15%;scaleX:0.8,1;scaleY:0.8,1;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-5,5", + }, + { + name: "ghostball_h", + syntax: "ghostball2|0;x:75%,75%|1;(ease:sine,yoyoEase:sine,repeat:-1,yoyo:true,delay:0.9);y:50%,55%;scaleX:0.8,1;scaleY:0.8,1;alpha:0,1|0.25;(repeat:-1,yoyo:true);rotation:-5,5", + }, + ], + }, }, - "sleeping": { + sleeping: { name: "sleeping", - fatype:"fas", - faname:"fa-bed", + fatype: "fas", + faname: "fa-bed", image: "modules/theatre/app/graphics/emotes/sleeping.png", - label:game.i18n.localize("Theatre.Emote.Sleeping"), + label: game.i18n.localize("Theatre.Emote.Sleeping"), rigging: { animations: [ - {name: "sleeping", syntax:"sleeping|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1"}, - {name: "zzz_a", syntax:"zzz|4;(repeat:-1,delay:0);y:25%,-20%;alpha:0,1;scaleX:0.1,1;scaleY:0.1,1|1;(ease:sineInOut,repeat:-1,delay:0,yoyo:true);x:30%,40%"}, - {name: "zzz_b", syntax:"zzz|4;(repeat:-1,delay:1);y:25%,-20%;alpha:0,1;scaleX:0.1,1;scaleY:0.1,1|1;(ease:sineInOut,repeat:-1,delay:0.5,yoyo:true);x:30%,40%"}, - {name: "zzz_c", syntax:"zzz|4;(repeat:-1,delay:2);y:25%,-20%;alpha:0,1;scaleX:0.1,1;scaleY:0.1,1|1;(ease:sineInOut,repeat:-1,delay:1,yoyo:true);x:30%,40%"}, - {name: "zzz_d", syntax:"zzz|4;(repeat:-1,delay:3);y:25%,-20%;alpha:0,1;scaleX:0.1,1;scaleY:0.1,1|1;(ease:sineInOut,repeat:-1,delay:1.5,yoyo:true);x:30%,40%"} - ] - } - } - }; + { name: "sleeping", syntax: "sleeping|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, + { + name: "zzz_a", + syntax: "zzz|4;(repeat:-1,delay:0);y:25%,-20%;alpha:0,1;scaleX:0.1,1;scaleY:0.1,1|1;(ease:sineInOut,repeat:-1,delay:0,yoyo:true);x:30%,40%", + }, + { + name: "zzz_b", + syntax: "zzz|4;(repeat:-1,delay:1);y:25%,-20%;alpha:0,1;scaleX:0.1,1;scaleY:0.1,1|1;(ease:sineInOut,repeat:-1,delay:0.5,yoyo:true);x:30%,40%", + }, + { + name: "zzz_c", + syntax: "zzz|4;(repeat:-1,delay:2);y:25%,-20%;alpha:0,1;scaleX:0.1,1;scaleY:0.1,1|1;(ease:sineInOut,repeat:-1,delay:1,yoyo:true);x:30%,40%", + }, + { + name: "zzz_d", + syntax: "zzz|4;(repeat:-1,delay:3);y:25%,-20%;alpha:0,1;scaleX:0.1,1;scaleY:0.1,1|1;(ease:sineInOut,repeat:-1,delay:1.5,yoyo:true);x:30%,40%", + }, + ], + }, + }, + }; } /** - * Split to chars, logically group words based on language. + * Split to chars, logically group words based on language. * * @param text (String) : The text to split. - * @param textBox (HTMLElement) : The textBox the text will be contained in. + * @param textBox (HTMLElement) : The textBox the text will be contained in. * * @return (Array[HTMLElement]) : An array of HTMLElements of the split text. */ - static splitTextBoxToChars(text,textBox) { - let charSpans = []; - let fontSize = Number(KHelpers.style(textBox)["font-size"].match(/\-*\d+\.*\d*/) || 0); - let splitMode = 1; + static splitTextBoxToChars(text, textBox) { + let charSpans = []; + let fontSize = Number(KHelpers.style(textBox)["font-size"].match(/\-*\d+\.*\d*/) || 0); + let splitMode = 1; // we have 2 modes, if we're a latin based language, or a language that does word // grouping of characters, we should attempt to preserve words by collecting // character spans into divs. // If we're a language that is symbol based, and don't care about word groupings - // then we just out a stream of characters without regard to groupings. + // then we just out a stream of characters without regard to groupings. // // switch (game.i18n.lang) { case "ja": // Kinsoku Shori (JP) - splitMode = 3; - break; + splitMode = 3; + break; case "cn": // 按照日文方式换行 (CN) - splitMode = 3; - break; + splitMode = 3; + break; case "ko": - // KS X ISO/IEC 26300:2007 (KO) - splitMode = 4; - break; + // KS X ISO/IEC 26300:2007 (KO) + splitMode = 4; + break; case "zh": case "th": // word break with impunity - splitMode = 1; - break; + splitMode = 1; + break; default: // don't word break - splitMode = 2; - break; + splitMode = 2; + break; } if (splitMode == 1) { @@ -7613,296 +7483,285 @@ class Theatre { for (let c of text) { if (c == " ") { let cspan = document.createElement("span"); - cspan.textContent = c; - cspan.style.height = `${fontSize}px`; - cspan.style.width = `${fontSize/4}px`; - cspan.style.position = "relative"; - textBox.appendChild(cspan); - charSpans.push(cspan); + cspan.textContent = c; + cspan.style.height = `${fontSize}px`; + cspan.style.width = `${fontSize / 4}px`; + cspan.style.position = "relative"; + textBox.appendChild(cspan); + charSpans.push(cspan); } else if (c == "\n") { let cspan = document.createElement("hr"); - textBox.appendChild(cspan); + textBox.appendChild(cspan); } else { let cspan = document.createElement("span"); - cspan.textContent = c; - cspan.style.height = `${fontSize}px`; - cspan.style.position = "relative"; - textBox.appendChild(cspan); - charSpans.push(cspan); + cspan.textContent = c; + cspan.style.height = `${fontSize}px`; + cspan.style.position = "relative"; + textBox.appendChild(cspan); + charSpans.push(cspan); } // relative positioning } } else if (splitMode == 2) { // split chars, group words - let word = document.createElement("div"); - let prevChar = ""; - word.style.height = `${fontSize}px`; - word.style.position = "relative"; + let word = document.createElement("div"); + let prevChar = ""; + word.style.height = `${fontSize}px`; + word.style.position = "relative"; for (let c of text) { if (c == " ") { let cspan = document.createElement("span"); - cspan.textContent = c; - cspan.style.height = `${fontSize}px`; - cspan.style.width = `${fontSize/4}px`; + cspan.textContent = c; + cspan.style.height = `${fontSize}px`; + cspan.style.width = `${fontSize / 4}px`; // not part of an extended white space, append word, start new one if (prevChar != " " && prevChar != "\n") { - textBox.appendChild(word); - word = document.createElement("div"); - word.style.height = `${fontSize}px`; - word.style.position = "relative"; + textBox.appendChild(word); + word = document.createElement("div"); + word.style.height = `${fontSize}px`; + word.style.position = "relative"; } - textBox.appendChild(cspan); - cspan.style.position = "relative"; - charSpans.push(cspan); + textBox.appendChild(cspan); + cspan.style.position = "relative"; + charSpans.push(cspan); } else if (c == "\n") { let cspan = document.createElement("hr"); if (prevChar != " " && prevChar != "\n") { - textBox.appendChild(word); - word = document.createElement("div"); - word.style.height = `${fontSize}px`; - word.style.position = "relative"; + textBox.appendChild(word); + word = document.createElement("div"); + word.style.height = `${fontSize}px`; + word.style.position = "relative"; } - textBox.appendChild(cspan); + textBox.appendChild(cspan); } else { let cspan = document.createElement("span"); - cspan.textContent = c; - cspan.style.height = `${fontSize}px`; + cspan.textContent = c; + cspan.style.height = `${fontSize}px`; // we're part of a word - cspan.style.position = "relative"; - word.appendChild(cspan); - charSpans.push(cspan); + cspan.style.position = "relative"; + word.appendChild(cspan); + charSpans.push(cspan); } // prevChar - prevChar = c; + prevChar = c; } - textBox.append(word); + textBox.append(word); } else if (splitMode == 3) { // Kinsoku Shori (JP) let rHead = "))]}〕〉》」』】〙〗〟'\"⦆»ヽヾーァィゥェォッャュョヮヵヶぁぃぅぇぉっゃゅょゎゕゖㇰㇱㇲㇳㇴㇵㇶㇷㇸㇹㇺㇻㇼㇽㇾㇿ々〻‐゠–〜? ! ‼ ⁇ ⁈ ⁉・、:;,。."; - let rTail = "(([{〔〈《「『【〘〖〝'\"⦅«"; - let rSplit = "—.‥〳〴〵"; - let word = null; - for (let idx=0; idx= 2 && !rt && !rh && !rs && !nv) { textBox.appendChild(word); - word = null; + word = null; } if (nl) { // newline after word if present let cspan = document.createElement("hr"); if (word) { - textBox.appendChild(word); - word = null; + textBox.appendChild(word); + word = null; } - textBox.appendChild(cspan); + textBox.appendChild(cspan); } else if (sp) { // if not a newline, but a space output word before space if (word) { - textBox.appendChild(word); - word = null; + textBox.appendChild(word); + word = null; } let cspan = document.createElement("span"); - cspan.textContent = c; - cspan.style.height = `${fontSize}px`; - cspan.style.width = `${fontSize/4}px`; - cspan.style.position = "relative"; - textBox.appendChild(cspan); - charSpans.push(cspan); + cspan.textContent = c; + cspan.style.height = `${fontSize}px`; + cspan.style.width = `${fontSize / 4}px`; + cspan.style.position = "relative"; + textBox.appendChild(cspan); + charSpans.push(cspan); } - } if (word) { - textBox.appendChild(word); - word = null; + textBox.appendChild(word); + word = null; } } else if (splitMode == 4) { - // Korean Line breaking KS X ISO/IEC 26300:2007 (KO) + // Korean Line breaking KS X ISO/IEC 26300:2007 (KO) let rHead = "!%),.:;?]}¢°'\"†‡℃〆〈《「『〕!%),.:;?]} "; - let rTail = "$([\\{£¥'\"々〇〉》」〔$([{⦆¥₩#"; - let word = null; - for (let idx=0; idx= 2 && !rh && !rt && !rs && !nv) { textBox.appendChild(word); - word = null; + word = null; } if (nl) { // newline after word if present let cspan = document.createElement("hr"); if (word) { - textBox.appendChild(word); - word = null; + textBox.appendChild(word); + word = null; } - textBox.appendChild(cspan); + textBox.appendChild(cspan); } - } if (word) { - textBox.appendChild(word); - word = null; + textBox.appendChild(word); + word = null; } - } - - return charSpans; + + return charSpans; } /** @@ -7911,21 +7770,21 @@ class Theatre { * * @params ev (Event) : The event that triggered the configuration option. * @params actorSheet (Object ActorSheet) : The ActorSheet Object to spawn a configure - * window from. + * window from. */ - static onConfigureInsert(ev,actorSheet) { - ev.preventDefault(); - if (Theatre.DEBUG) console.log("Click Event on Configure Theatre!!!",actorSheet,actorSheet.actor,actorSheet.position); + static onConfigureInsert(ev, actorSheet) { + ev.preventDefault(); + if (Theatre.DEBUG) console.log("Click Event on Configure Theatre!!!", actorSheet, actorSheet.actor, actorSheet.position); if (!actorSheet.actor.data.flags.theatre) { - actorSheet.actor.data.flags.theatre = {baseinsert:"", name:""}; + actorSheet.actor.data.flags.theatre = { baseinsert: "", name: "" }; } new TheatreActorConfig(actorSheet.actor, { - top: actorSheet.position.top+40, - left: actorSheet.position.left + ((actorSheet.position.width - 500) / 2), - configureDefault: true - }).render(true); + top: actorSheet.position.top + 40, + left: actorSheet.position.left + (actorSheet.position.width - 500) / 2, + configureDefault: true, + }).render(true); } /** @@ -7933,34 +7792,34 @@ class Theatre { * * @params ev (Event) : The event that triggered adding to the NavBar staging area. */ - static onAddToNavBar(ev,actorSheet,removeLabelSheetHeader) { - if (Theatre.DEBUG) console.log("Click Event on Add to NavBar!!",actorSheet,actorSheet.actor,actorSheet.position); - const actor = actorSheet.object.data; + static onAddToNavBar(ev, actorSheet, removeLabelSheetHeader) { + if (Theatre.DEBUG) console.log("Click Event on Add to NavBar!!", actorSheet, actorSheet.actor, actorSheet.position); + const actor = actorSheet.object.data; const addLabel = removeLabelSheetHeader ? "" : game.i18n.localize("Theatre.UI.Config.AddToStage"); const removeLabel = removeLabelSheetHeader ? "" : game.i18n.localize("Theatre.UI.Config.RemoveFromStage"); let newText; if (Theatre.isActorStaged(actor)) { - Theatre.removeFromNavBar(actor) - newText = addLabel + Theatre.removeFromNavBar(actor); + newText = addLabel; } else { - Theatre.addToNavBar(actor); + Theatre.addToNavBar(actor); newText = removeLabel; } - ev.currentTarget.innerHTML = Theatre.isActorStaged(actor) ? `${newText}` : `${newText}`; + ev.currentTarget.innerHTML = Theatre.isActorStaged(actor) ? `${newText}` : `${newText}`; } static _getTheatreId(actor) { - return `theatre-${actor._id}`; + return `theatre-${actor._id}`; } /** * Add to the NavBar staging area * - * @params actor (Actor) : The actor from which to add to the NavBar staging area. + * @params actor (Actor) : The actor from which to add to the NavBar staging area. */ static addToNavBar(actor) { - if (!actor) return; - if (Theatre.DEBUG) console.log("actor is valid!"); + if (!actor) return; + if (Theatre.DEBUG) console.log("actor is valid!"); // if already on stage, dont add it again // create nav-list-item // set picture as actor.data.img @@ -7970,53 +7829,49 @@ class Theatre { // from the bar // add click handler logic to remove it from the stage let theatreId = Theatre._getTheatreId(actor); - let portrait = (actor.img ? actor.img : "icons/mystery-man.png"); - let optAlign = "top"; - let name = actor.name; + let portrait = actor.img ? actor.img : "icons/mystery-man.png"; + let optAlign = "top"; + let name = actor.name; - if (!Theatre.instance.isActorOwner(game.user.id,theatreId)) { + if (!Theatre.instance.isActorOwner(game.user.id, theatreId)) { ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.DoNotControl")); - return; + return; } // Use defaults incase the essential flag attributes are missing if (actor.flags.theatre) { - if (actor.flags.theatre.name && actor.flags.theatre.name != "") - name = actor.flags.theatre.name; - if (actor.flags.theatre.baseinsert && actor.flags.theatre.baseinsert != "") - portrait = actor.flags.theatre.baseinsert; - if (actor.flags.theatre.optalign && actor.flags.theatre.optalign != "") - optAlign = actor.flags.theatre.optalign; + if (actor.flags.theatre.name && actor.flags.theatre.name != "") name = actor.flags.theatre.name; + if (actor.flags.theatre.baseinsert && actor.flags.theatre.baseinsert != "") portrait = actor.flags.theatre.baseinsert; + if (actor.flags.theatre.optalign && actor.flags.theatre.optalign != "") optAlign = actor.flags.theatre.optalign; } if (Theatre.instance.stage[theatreId]) { ui.notifications.info(actor.name + game.i18n.localize("Theatre.UI.Notification.AlreadyStaged")); - return; + return; } - if (Theatre.DEBUG) console.log("new theatre id: " + theatreId); + if (Theatre.DEBUG) console.log("new theatre id: " + theatreId); let navItem = document.createElement("img"); - KHelpers.addClass(navItem,"theatre-control-nav-bar-item"); - //navItem.setAttribute("draggable",false); - navItem.setAttribute("imgId",theatreId); - navItem.setAttribute("src",portrait); - navItem.setAttribute("title",name + (name == actor.name ? "" : ` (${actor.name})`)); - navItem.setAttribute("name",name); - navItem.setAttribute("optalign",optAlign); + KHelpers.addClass(navItem, "theatre-control-nav-bar-item"); + //navItem.setAttribute("draggable",false); + navItem.setAttribute("imgId", theatreId); + navItem.setAttribute("src", portrait); + navItem.setAttribute("title", name + (name == actor.name ? "" : ` (${actor.name})`)); + navItem.setAttribute("name", name); + navItem.setAttribute("optalign", optAlign); // if the theatreId is present, then set our navItem as active! - if (!!Theatre.instance.getInsertById(theatreId)) - KHelpers.addClass(navItem,"theatre-control-nav-bar-item-active"); - - navItem.addEventListener("mouseup",Theatre.instance.handleNavItemMouseUp); - navItem.addEventListener("dragstart",Theatre.instance.handleNavItemDragStart); - navItem.addEventListener("dragend",Theatre.instance.handleNavItemDragEnd); - navItem.addEventListener("dragover",Theatre.instance.handleNavItemDragOver); - navItem.addEventListener("drop",Theatre.instance.handleNavItemDragDrop); - Theatre.instance.theatreNavBar.appendChild(navItem); + if (!!Theatre.instance.getInsertById(theatreId)) KHelpers.addClass(navItem, "theatre-control-nav-bar-item-active"); + + navItem.addEventListener("mouseup", Theatre.instance.handleNavItemMouseUp); + navItem.addEventListener("dragstart", Theatre.instance.handleNavItemDragStart); + navItem.addEventListener("dragend", Theatre.instance.handleNavItemDragEnd); + navItem.addEventListener("dragover", Theatre.instance.handleNavItemDragOver); + navItem.addEventListener("drop", Theatre.instance.handleNavItemDragDrop); + Theatre.instance.theatreNavBar.appendChild(navItem); // stage event - Theatre.instance.stageInsertById(theatreId); + Theatre.instance.stageInsertById(theatreId); // Store reference Theatre.instance.stage[theatreId] = new TheatreActor(actor, navItem); } @@ -8024,13 +7879,12 @@ class Theatre { /** * Removes the actor from the nav bar. * - * @params actor (Actor) : The actor to remove from the NavBar staging area. + * @params actor (Actor) : The actor to remove from the NavBar staging area. */ static removeFromNavBar(actor) { - if (!actor) return; + if (!actor) return; const theatreId = Theatre._getTheatreId(actor); Theatre.instance._removeFromStage(theatreId); - } /** @@ -8038,10 +7892,10 @@ class Theatre { * * @params id (string) : The theatreId to remove from the stage. */ - _removeFromStage(theatreId) { + _removeFromStage(theatreId) { const staged = Theatre.instance.stage[theatreId]; - if(staged) { - if(staged.navElement) { + if (staged) { + if (staged.navElement) { Theatre.instance.theatreNavBar.removeChild(staged.navElement); } Theatre.instance.removeInsertById(theatreId); @@ -8051,17 +7905,17 @@ class Theatre { /** * Returns whether the actor is on the stage. - * @params actor (Actor) : The actor. + * @params actor (Actor) : The actor. */ static isActorStaged(actor) { - if (!actor) return false; - return !!Theatre.instance.stage[Theatre._getTheatreId(actor)] + if (!actor) return false; + return !!Theatre.instance.stage[Theatre._getTheatreId(actor)]; } static clearStage() { - Object.keys(Theatre.instance.stage).forEach(theatreId => { + Object.keys(Theatre.instance.stage).forEach((theatreId) => { Theatre._removeFromStage(theatreId); - }) + }); } /** @@ -8070,203 +7924,194 @@ class Theatre { * @param name (String) : The name of the standing text animation to get. * * @return (Object) : An Object tuple of {func: (Function), label: (String)} - * representing the animation function and function label. - * + * representing the animation function and function label. + * */ static textStandingAnimation(name) { if (!Theatre.STANDING_ANIMS) Theatre.STANDING_ANIMS = { - - "impact" : { - "func" : function(target, shakeradius) { - if (!target) return; - shakeradius = shakeradius || Math.random()*7+7; - shakeradius = Math.max(shakeradius - Math.random()*0.5, 0); + impact: { + func: function (target, shakeradius) { + if (!target) return; + shakeradius = shakeradius || Math.random() * 7 + 7; + shakeradius = Math.max(shakeradius - Math.random() * 0.5, 0); // Impact complete! if (shakeradius == 0) { - target.style.left = "0px"; - target.style.top = "0px"; - return; + target.style.left = "0px"; + target.style.top = "0px"; + return; } TweenMax.to(target, 0.025, { - left: `${(Math.random() < 0.5 ? -1 : 1) * Math.random()*shakeradius}px`, - top: `${(Math.random() < 0.5 ? -1 : 1) * Math.random()*shakeradius}px`, + left: `${(Math.random() < 0.5 ? -1 : 1) * Math.random() * shakeradius}px`, + top: `${(Math.random() < 0.5 ? -1 : 1) * Math.random() * shakeradius}px`, onComplete: Theatre.textStandingAnimation("impact"), - onCompleteParams: [target,shakeradius] - }); + onCompleteParams: [target, shakeradius], + }); }, - "label" : game.i18n.localize("Theatre.Standing.Impact") + label: game.i18n.localize("Theatre.Standing.Impact"), }, - "quiver" : { - "func" : function(target,quiverAmt) { - if (!target) return; - quiverAmt = quiverAmt || 2; - quiverAmt = Math.max(quiverAmt - Math.random()*0.1, 0); + quiver: { + func: function (target, quiverAmt) { + if (!target) return; + quiverAmt = quiverAmt || 2; + quiverAmt = Math.max(quiverAmt - Math.random() * 0.1, 0); // Waver complete if (quiverAmt == 0) { - target.style.left = "0px"; - target.style.top = "0px"; - return; + target.style.left = "0px"; + target.style.top = "0px"; + return; } TweenMax.to(target, 0.1, { - left: `${(Math.random() < 0.5 ? -1 : 1) * Math.random()*quiverAmt}px`, - top: `${(Math.random() < 0.5 ? -1 : 1) * Math.random()*quiverAmt}px`, + left: `${(Math.random() < 0.5 ? -1 : 1) * Math.random() * quiverAmt}px`, + top: `${(Math.random() < 0.5 ? -1 : 1) * Math.random() * quiverAmt}px`, onComplete: Theatre.textStandingAnimation("quiver"), - onCompleteParams: [target,quiverAmt] - }); + onCompleteParams: [target, quiverAmt], + }); }, - "label" : game.i18n.localize("Theatre.Standing.Quiver") + label: game.i18n.localize("Theatre.Standing.Quiver"), }, - "wave" : { - "func" : function(target,waveAmp) { - if (!target) return; - waveAmp = waveAmp || 4; - if (waveAmp > 0) - waveAmp = waveAmp - 0.5 - else - waveAmp = waveAmp + 0.5 + wave: { + func: function (target, waveAmp) { + if (!target) return; + waveAmp = waveAmp || 4; + if (waveAmp > 0) waveAmp = waveAmp - 0.5; + else waveAmp = waveAmp + 0.5; // Waver complete if (waveAmp == 0) { - target.style.top = "0px"; - return; + target.style.top = "0px"; + return; } TweenMax.to(target, 0.5, { top: `${waveAmp}px`, onComplete: Theatre.textStandingAnimation("wave"), - onCompleteParams: [target,-waveAmp] - }); + onCompleteParams: [target, -waveAmp], + }); }, - "label" : game.i18n.localize("Theatre.Standing.Wave") + label: game.i18n.localize("Theatre.Standing.Wave"), }, - "fade" : { - "func" : function(target,fade) { - if (!target) return; - fade = fade || 1; - fade = Math.max(fade - 0.025, 0); + fade: { + func: function (target, fade) { + if (!target) return; + fade = fade || 1; + fade = Math.max(fade - 0.025, 0); // fade complete if (fade <= 0) { - target.style.opacity = 0; - return; + target.style.opacity = 0; + return; } TweenMax.to(target, 0.1, { opacity: fade, onComplete: Theatre.textStandingAnimation("fade"), - onCompleteParams: [target,fade] - }); + onCompleteParams: [target, fade], + }); }, - "label" : game.i18n.localize("Theatre.Standing.Fade") + label: game.i18n.localize("Theatre.Standing.Fade"), }, - "excited" : { - "func" : function(target) { - if (!target) return; + excited: { + func: function (target) { + if (!target) return; TweenMax.to(target, 0.025, { - left: `${(Math.random() < 0.5 ? -1 : 1) * Math.random()*1}px`, - top: `${(Math.random() < 0.5 ? -1 : 1) * Math.random()*1}px`, + left: `${(Math.random() < 0.5 ? -1 : 1) * Math.random() * 1}px`, + top: `${(Math.random() < 0.5 ? -1 : 1) * Math.random() * 1}px`, onComplete: Theatre.textStandingAnimation("excited"), - onCompleteParams: [target] - }); + onCompleteParams: [target], + }); }, - "label" : game.i18n.localize("Theatre.Standing.Excited") + label: game.i18n.localize("Theatre.Standing.Excited"), }, - "violent" : { - "func" : function(target, oshakeradius, ox, oy) { - if (!target) return; - ox = ox || 0; - oy = oy || 0; - oshakeradius = oshakeradius || 2; - let shakeradius = Math.random()*oshakeradius+oshakeradius; - if (!target.style.left.match("0px") || !target.style.top.match("0px")) - shakeradius = 0; + violent: { + func: function (target, oshakeradius, ox, oy) { + if (!target) return; + ox = ox || 0; + oy = oy || 0; + oshakeradius = oshakeradius || 2; + let shakeradius = Math.random() * oshakeradius + oshakeradius; + if (!target.style.left.match("0px") || !target.style.top.match("0px")) shakeradius = 0; TweenMax.to(target, 0.025, { - left: `${(Math.random() < 0.5 ? -1 : 1) * Math.random()*shakeradius+ox}px`, - top: `${(Math.random() < 0.5 ? -1 : 1) * Math.random()*shakeradius+oy}px`, - scale: `${Math.random()/3 + 0.9}`, + left: `${(Math.random() < 0.5 ? -1 : 1) * Math.random() * shakeradius + ox}px`, + top: `${(Math.random() < 0.5 ? -1 : 1) * Math.random() * shakeradius + oy}px`, + scale: `${Math.random() / 3 + 0.9}`, onComplete: Theatre.textStandingAnimation("violent"), - onCompleteParams: [target,oshakeradius,ox,oy] - }); + onCompleteParams: [target, oshakeradius, ox, oy], + }); }, - "label" : game.i18n.localize("Theatre.Standing.Violent") + label: game.i18n.localize("Theatre.Standing.Violent"), }, - "bubbly" : { - "func" : function(target) { - if (!target) return; + bubbly: { + func: function (target) { + if (!target) return; TweenMax.to(target, 0.5, { - scale: `${Math.floor((Math.random()*0.4+0.8)*100)/100}`, + scale: `${Math.floor((Math.random() * 0.4 + 0.8) * 100) / 100}`, onComplete: Theatre.textStandingAnimation("bubbly"), - onCompleteParams: [target] - }); + onCompleteParams: [target], + }); }, - "label" : game.i18n.localize("Theatre.Standing.Bubbly") + label: game.i18n.localize("Theatre.Standing.Bubbly"), }, - "spooky" : { - "func" : function(target) { - if (!target) return; - TweenMax.to(target,Math.floor((Math.random()*0.25+0.2)*100)/100, { - left: `${(Math.random() < 0.5 ? -1 : 1) * Math.random()*3}px`, - top: `${(Math.random() < 0.5 ? -1 : 1) * Math.random()*3}px`, + spooky: { + func: function (target) { + if (!target) return; + TweenMax.to(target, Math.floor((Math.random() * 0.25 + 0.2) * 100) / 100, { + left: `${(Math.random() < 0.5 ? -1 : 1) * Math.random() * 3}px`, + top: `${(Math.random() < 0.5 ? -1 : 1) * Math.random() * 3}px`, onComplete: Theatre.textStandingAnimation("spooky"), - onCompleteParams: [target] - }); + onCompleteParams: [target], + }); }, - "label" : game.i18n.localize("Theatre.Standing.Spooky") + label: game.i18n.localize("Theatre.Standing.Spooky"), }, - "insane" : { - "func" : function(target, rotation, scale) { - if (!target) return; - let spin = (Math.random() * 100); - let grow = (Math.random() * 200); - let animtime = 0.025; - rotation = rotation || 0; - scale = scale || 1; + insane: { + func: function (target, rotation, scale) { + if (!target) return; + let spin = Math.random() * 100; + let grow = Math.random() * 200; + let animtime = 0.025; + rotation = rotation || 0; + scale = scale || 1; if (spin >= 99.95) { - animtime = Math.random()*0.5; - rotation = 1080; + animtime = Math.random() * 0.5; + rotation = 1080; } else if (spin >= 99.8) { - animtime = Math.random()*0.5 + 0.5; - rotation = 360; + animtime = Math.random() * 0.5 + 0.5; + rotation = 360; } else if (spin >= 80) { - rotation = (rotation != 0 ? 0 : (Math.random() < 0.5 ? -1 : 1) * Math.floor(Math.random()*30)); + rotation = rotation != 0 ? 0 : (Math.random() < 0.5 ? -1 : 1) * Math.floor(Math.random() * 30); } if (grow >= 199) { - if (scale != 1) - scale = 1; - else - scale = Math.random() * 0.5 + 1; + if (scale != 1) scale = 1; + else scale = Math.random() * 0.5 + 1; } - TweenMax.to(target, animtime, { - left: `${(Math.random() < 0.5 ? -1 : 1) * Math.random()*1}px`, - top: `${(Math.random() < 0.5 ? -1 : 1) * Math.random()*1}px`, + left: `${(Math.random() < 0.5 ? -1 : 1) * Math.random() * 1}px`, + top: `${(Math.random() < 0.5 ? -1 : 1) * Math.random() * 1}px`, rotation: rotation, scale: scale, onComplete: Theatre.textStandingAnimation("insane"), - onCompleteParams: [target,rotation,scale] - }); + onCompleteParams: [target, rotation, scale], + }); }, - "label" : game.i18n.localize("Theatre.Standing.Insane") - } - + label: game.i18n.localize("Theatre.Standing.Insane"), + }, }; - if (Theatre.STANDING_ANIMS[name]) - return Theatre.STANDING_ANIMS[name].func; + if (Theatre.STANDING_ANIMS[name]) return Theatre.STANDING_ANIMS[name].func; } /** @@ -8279,368 +8124,330 @@ class Theatre { * @params name (String) : The name of the fly-in animation to use * * @return (Object) : An Object tuple of {func: (Function), label: (String)} - * representing the animation function and function label. + * representing the animation function and function label. * */ static textFlyinAnimation(name) { if (!Theatre.FLYIN_ANIMS) Theatre.FLYIN_ANIMS = { - "typewriter" : { - "func" : function(charSpans,animTime,speed,standingAnim) { - gsap.from(charSpans,{ - duration: 0.05, - stagger: { - each: 0.05, - onComplete: function() { - if (standingAnim) - standingAnim.call(this, this.targets()[0]); - } - }, + typewriter: { + func: function (charSpans, animTime, speed, standingAnim) { + gsap.from(charSpans, { + duration: 0.05, + stagger: { + each: 0.05, + onComplete: function () { + if (standingAnim) standingAnim.call(this, this.targets()[0]); + }, + }, opacity: 0, - scale: 1.5 - }); - + scale: 1.5, + }); }, - "label" : game.i18n.localize("Theatre.Flyin.Typewriter") + label: game.i18n.localize("Theatre.Flyin.Typewriter"), }, - "fadein" : { - "func" : function(charSpans,animTime,speed,standingAnim) { - gsap.from(charSpans,{ - duration: animTime, - stagger: { - each: speed, - onComplete: function() { - if (standingAnim) - standingAnim.call(this, this.targets()[0]); - } - }, + fadein: { + func: function (charSpans, animTime, speed, standingAnim) { + gsap.from(charSpans, { + duration: animTime, + stagger: { + each: speed, + onComplete: function () { + if (standingAnim) standingAnim.call(this, this.targets()[0]); + }, + }, opacity: 0, - }); + }); }, - "label" : game.i18n.localize("Theatre.Flyin.Fadein") + label: game.i18n.localize("Theatre.Flyin.Fadein"), }, - "slidein" : { - "func" : function(charSpans,animTime,speed,standingAnim) { - gsap.from(charSpans, - { - duration: animTime, - stagger: { - each: speed, - onComplete: function() { - if (standingAnim) - standingAnim.call(this, this.targets()[0]); - } - }, - opacity: 0, - left: 200 - } - ); + slidein: { + func: function (charSpans, animTime, speed, standingAnim) { + gsap.from(charSpans, { + duration: animTime, + stagger: { + each: speed, + onComplete: function () { + if (standingAnim) standingAnim.call(this, this.targets()[0]); + }, + }, + opacity: 0, + left: 200, + }); }, - "label" : game.i18n.localize("Theatre.Flyin.Slidein") + label: game.i18n.localize("Theatre.Flyin.Slidein"), }, - "scalein" : { - "func" : function(charSpans,animTime,speed,standingAnim) { - gsap.from(charSpans, - { - duration: animTime, - stagger: { - each: speed, - onComplete: function() { - if (standingAnim) - standingAnim.call(this, this.targets()[0]); - } - }, - opacity: 0, - scale: 5, - //rotation: -180, - ease: Power4.easeOut - } - ); + scalein: { + func: function (charSpans, animTime, speed, standingAnim) { + gsap.from(charSpans, { + duration: animTime, + stagger: { + each: speed, + onComplete: function () { + if (standingAnim) standingAnim.call(this, this.targets()[0]); + }, + }, + opacity: 0, + scale: 5, + //rotation: -180, + ease: Power4.easeOut, + }); }, - "label" : game.i18n.localize("Theatre.Flyin.Scalein") + label: game.i18n.localize("Theatre.Flyin.Scalein"), }, - "fallin" : { - "func" : function(charSpans,animTime,speed,standingAnim) { - let textBox = null; + fallin: { + func: function (charSpans, animTime, speed, standingAnim) { + let textBox = null; if (charSpans[0]) { switch (Theatre.instance.settings.theatreStyle) { case "lightbox": - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box-light",5); - if (!textBox) - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box",5); - break; + textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box-light", 5); + if (!textBox) textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box", 5); + break; case "clearbox": - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box-clear",5); - if (!textBox) - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box",5); - break; + textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box-clear", 5); + if (!textBox) textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box", 5); + break; case "mangabubble": - break; + break; case "textbox": default: - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box",5); - break; + textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box", 5); + break; } if (textBox) { - textBox.style["overflow-y"] = "visible"; - textBox.style["overflow-x"] = "visible"; + textBox.style["overflow-y"] = "visible"; + textBox.style["overflow-x"] = "visible"; } } - gsap.from(charSpans, - { - duration: animTime, - stagger: { - each: speed, - onComplete: function() { - if (standingAnim) - standingAnim.call(this, this.targets()[0]); - } - }, - opacity: 0, - top: -100, - ease: Power4.easeOut, - onComplete: () => { - if (Theatre.DEBUG) console.log("completeAll"); - if (textBox) { - textBox.style["overflow-y"] = "scroll"; - textBox.style["overflow-x"] = "hidden"; - } + gsap.from(charSpans, { + duration: animTime, + stagger: { + each: speed, + onComplete: function () { + if (standingAnim) standingAnim.call(this, this.targets()[0]); + }, + }, + opacity: 0, + top: -100, + ease: Power4.easeOut, + onComplete: () => { + if (Theatre.DEBUG) console.log("completeAll"); + if (textBox) { + textBox.style["overflow-y"] = "scroll"; + textBox.style["overflow-x"] = "hidden"; } - } - ); + }, + }); }, - "label" : game.i18n.localize("Theatre.Flyin.Fallin") + label: game.i18n.localize("Theatre.Flyin.Fallin"), }, - - "spin" : { - "func" : function(charSpans,animTime,speed,standingAnim) { - gsap.from(charSpans, - { - duration: animTime, - stagger: { - each: speed, - onComplete: function() { - if (standingAnim) - standingAnim.call(this, this.targets()[0]); - } - }, - opacity: 0, - rotation: -360, - left: 100, - ease: Power4.easeOut - } - ); + spin: { + func: function (charSpans, animTime, speed, standingAnim) { + gsap.from(charSpans, { + duration: animTime, + stagger: { + each: speed, + onComplete: function () { + if (standingAnim) standingAnim.call(this, this.targets()[0]); + }, + }, + opacity: 0, + rotation: -360, + left: 100, + ease: Power4.easeOut, + }); }, - "label" : game.i18n.localize("Theatre.Flyin.Spin") + label: game.i18n.localize("Theatre.Flyin.Spin"), }, - "spinscale" : { - "func" : function(charSpans,animTime,speed,standingAnim) { - let textBox = null; + spinscale: { + func: function (charSpans, animTime, speed, standingAnim) { + let textBox = null; if (charSpans[0]) { switch (Theatre.instance.settings.theatreStyle) { case "lightbox": - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box-light",5); - if (!textBox) - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box",5); - break; + textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box-light", 5); + if (!textBox) textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box", 5); + break; case "clearbox": - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box-clear",5); - if (!textBox) - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box",5); - break; + textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box-clear", 5); + if (!textBox) textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box", 5); + break; case "mangabubble": - break; + break; case "textbox": default: - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box",5); - break; + textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box", 5); + break; } if (textBox) { - textBox.style["overflow-y"] = "visible"; - textBox.style["overflow-x"] = "visible"; + textBox.style["overflow-y"] = "visible"; + textBox.style["overflow-x"] = "visible"; } } - gsap.from(charSpans,animTime*1.5, - { - duration: animTime*1.5, - stagger: { - each: speed, - onComplete: function() { - if (standingAnim) - standingAnim.call(this, this.targets()[0]); - } - }, - opacity: 0, - scale: 5, - rotation: -360, - left: 150, - ease: Power4.easeOut, - onComplete: () => { - if (Theatre.DEBUG) console.log("completeAll"); - if (textBox) { - textBox.style["overflow-y"] = "scroll"; - textBox.style["overflow-x"] = "hidden"; - } + gsap.from(charSpans, animTime * 1.5, { + duration: animTime * 1.5, + stagger: { + each: speed, + onComplete: function () { + if (standingAnim) standingAnim.call(this, this.targets()[0]); + }, + }, + opacity: 0, + scale: 5, + rotation: -360, + left: 150, + ease: Power4.easeOut, + onComplete: () => { + if (Theatre.DEBUG) console.log("completeAll"); + if (textBox) { + textBox.style["overflow-y"] = "scroll"; + textBox.style["overflow-x"] = "hidden"; } - } - ); + }, + }); }, - "label" : game.i18n.localize("Theatre.Flyin.SpinScale") + label: game.i18n.localize("Theatre.Flyin.SpinScale"), }, - "outlaw" : { - "func" : function(charSpans,animTime,speed,standingAnim) { + outlaw: { + func: function (charSpans, animTime, speed, standingAnim) { //let barTop = 0; //let barLeft = 0; - let textBox = null; + let textBox = null; if (charSpans[0]) { switch (Theatre.instance.settings.theatreStyle) { case "lightbox": - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box-light",5); - if (!textBox) - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box",5); - break; + textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box-light", 5); + if (!textBox) textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box", 5); + break; case "clearbox": - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box-clear",5); - if (!textBox) - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box",5); - break; + textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box-clear", 5); + if (!textBox) textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box", 5); + break; case "mangabubble": - break; + break; case "textbox": default: - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box",5); - break; + textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box", 5); + break; } if (textBox) { - textBox.style["overflow-y"] = "visible"; - textBox.style["overflow-x"] = "visible"; + textBox.style["overflow-y"] = "visible"; + textBox.style["overflow-x"] = "visible"; } } - gsap.from(charSpans, - { - duration: animTime*1.5, - stagger: { - each: speed, - onComplete: function() { - if (standingAnim) - standingAnim.call(this, this.targets()[0]); - } - }, - opacity: 0, - scale: 6, - rotation: -1080, - ease: Power4.easeOut, - onComplete: () => { - if (Theatre.DEBUG) console.log("completeAll"); - if (textBox) { - textBox.style["overflow-y"] = "scroll"; - textBox.style["overflow-x"] = "hidden"; - // shaking box - //TweenMax.killTweensOf(charSpans[0].parentNode.parentNode); - //charSpans[0].parentNode.parentNode.style.top = `${barTop}px`; - //charSpans[0].parentNode.parentNode.style.left = `${barLeft}px`; - } + gsap.from(charSpans, { + duration: animTime * 1.5, + stagger: { + each: speed, + onComplete: function () { + if (standingAnim) standingAnim.call(this, this.targets()[0]); + }, + }, + opacity: 0, + scale: 6, + rotation: -1080, + ease: Power4.easeOut, + onComplete: () => { + if (Theatre.DEBUG) console.log("completeAll"); + if (textBox) { + textBox.style["overflow-y"] = "scroll"; + textBox.style["overflow-x"] = "hidden"; + // shaking box + //TweenMax.killTweensOf(charSpans[0].parentNode.parentNode); + //charSpans[0].parentNode.parentNode.style.top = `${barTop}px`; + //charSpans[0].parentNode.parentNode.style.left = `${barLeft}px`; } - } - ); + }, + }); }, - "label" : game.i18n.localize("Theatre.Flyin.Outlaw") + label: game.i18n.localize("Theatre.Flyin.Outlaw"), }, - "vortex" : { - "func" : function(charSpans,animTime,speed,standingAnim) { - - let textBox = null; + vortex: { + func: function (charSpans, animTime, speed, standingAnim) { + let textBox = null; if (charSpans[0]) { switch (Theatre.instance.settings.theatreStyle) { case "lightbox": - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box-light",5); - if (!textBox) - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box",5); - break; + textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box-light", 5); + if (!textBox) textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box", 5); + break; case "clearbox": - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box-clear",5); - if (!textBox) - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box",5); - break; + textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box-clear", 5); + if (!textBox) textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box", 5); + break; case "mangabubble": - break; + break; case "textbox": default: - textBox = KHelpers.seekParentClass(charSpans[0],"theatre-text-box",5); - break; + textBox = KHelpers.seekParentClass(charSpans[0], "theatre-text-box", 5); + break; } if (textBox) { - textBox.style["overflow-y"] = "visible"; - textBox.style["overflow-x"] = "visible"; + textBox.style["overflow-y"] = "visible"; + textBox.style["overflow-x"] = "visible"; } } - for (let idx=0; idx. + * along with this program. If not, see . * */ @@ -29,14 +29,12 @@ * ============================================================ */ class TheatreActorConfig extends FormApplication { - constructor(object={}, options={}) { + constructor(object = {}, options = {}) { if (object._theatre_mod_configTab) { - options.tabs = [ - {navSelector: ".tabs", contentSelector: ".theatre-config-contents", initial: object._theatre_mod_configTab} - ]; - if (object._theatre_mod_configTab === "emotes") { - options.height = 775; - } + options.tabs = [{ navSelector: ".tabs", contentSelector: ".theatre-config-contents", initial: object._theatre_mod_configTab }]; + if (object._theatre_mod_configTab === "emotes") { + options.height = 775; + } } super(object, options); } @@ -49,71 +47,64 @@ class TheatreActorConfig extends FormApplication { options.id = "theatre-config"; options.template = "modules/theatre/app/templates/theatre_actor_config.html"; options.width = 500; - options.height = 270; - options.tabs = [ - {navSelector: ".tabs", contentSelector: ".theatre-config-contents", initial: "main"} - ]; - return options; - } - - /** - * Add the Entity name into the window title - */ - get title() { - return `${this.object.name}: ${game.i18n.localize("Theatre.UI.Config.ConfigureTheatre")}`; - } - - /** - * Construct and return the data object used to render the HTML template for this form application. + options.height = 270; + options.tabs = [{ navSelector: ".tabs", contentSelector: ".theatre-config-contents", initial: "main" }]; + return options; + } + + /** + * Add the Entity name into the window title + */ + get title() { + return `${this.object.name}: ${game.i18n.localize("Theatre.UI.Config.ConfigureTheatre")}`; + } + + /** + * Construct and return the data object used to render the HTML template for this form application. * - * @return (Object) : The Object to be used in handlebars compile - */ - getData() { - const entityName = this.object.name; - return { - entityName: entityName, - isGM: game.user.isGM, - object: duplicate(this.object.data), + * @return (Object) : The Object to be used in handlebars compile + */ + getData() { + const entityName = this.object.name; + return { + entityName: entityName, + isGM: game.user.isGM, + object: duplicate(this.object.data), emote: Theatre.getActorEmotes(this.object.data._id), - options: this.options, - } - } - - /** - * Activate the default set of listeners for the Actor Sheet - * These listeners handle basic stuff like form submission or updating images - * - * @param html (JQuery) The rendered template ready to have listeners attached - */ - activateListeners(html) { - super.activateListeners(html); + options: this.options, + }; + } + /** + * Activate the default set of listeners for the Actor Sheet + * These listeners handle basic stuff like form submission or updating images + * + * @param html (JQuery) The rendered template ready to have listeners attached + */ + activateListeners(html) { + super.activateListeners(html); - let btnAdd = html[0].getElementsByClassName("theatre-config-btn-add-emote")[0]; - if (btnAdd) - btnAdd.addEventListener("click",this._onAddEmoteLine.bind(this)); + let btnAdd = html[0].getElementsByClassName("theatre-config-btn-add-emote")[0]; + if (btnAdd) btnAdd.addEventListener("click", this._onAddEmoteLine.bind(this)); - let btnsEmoteConfig = html[0].getElementsByClassName("theatre-config-btn-edit-emote"); - for (let btn of btnsEmoteConfig) - btn.addEventListener("click",this._onEditEmoteLine.bind(this)); + let btnsEmoteConfig = html[0].getElementsByClassName("theatre-config-btn-edit-emote"); + for (let btn of btnsEmoteConfig) btn.addEventListener("click", this._onEditEmoteLine.bind(this)); - // Support custom icon updates - let iconsCustom = html[0].getElementsByClassName("customicon"); - for (let icon of iconsCustom) - icon.addEventListener("click",this._onCustomIconImage.bind(this)); + // Support custom icon updates + let iconsCustom = html[0].getElementsByClassName("customicon"); + for (let icon of iconsCustom) icon.addEventListener("click", this._onCustomIconImage.bind(this)); // Support custom label updates - let labelsCustom = html[0].getElementsByClassName("customlabel"); - for (let label of labelsCustom) - this._setupCustomLabelEvents(label); - } + let labelsCustom = html[0].getElementsByClassName("customlabel"); + for (let label of labelsCustom) this._setupCustomLabelEvents(label); + } /** @override */ _onChangeTab(event, tabs, active) { - this.object._theatre_mod_configTab = active; - // Auto change height - const tab = this.element.find(`.tab[data-tab="${active}"]`)[0]; - this.setPosition({height: (tab && tab.offsetHeight + 125) || "auto"}) + this.object._theatre_mod_configTab = active; + // Auto change height + const tab = this.element.find(`.tab[data-tab="${active}"]`)[0]; + this.setPosition({ height: (tab && tab.offsetHeight + 125) || "auto" }); } /** @@ -122,11 +113,10 @@ class TheatreActorConfig extends FormApplication { * @param formData (Object) : The object form data to be verified * * @return Object : an object containing the revised formData to be updated - * as well as a set of data which only contains the updated + * as well as a set of data which only contains the updated * emotes (excluding other theatre updates) */ _verifyCustomEmotes(formData) { - // find the formdata elements that contain "custom#" in their chain // once we find these objects, verify that there's a boolean attribute // specifying that it is a customEmote @@ -136,294 +126,271 @@ class TheatreActorConfig extends FormApplication { // then we add it to the form submission for (let k in formData) if (formData[k] && /emotes\.custom\d+/.test(k)) { - let mch = k.match(/flags\.theatre\.emotes\.custom\d+/)[0]; - let name = mch.match(/custom\d+/)[0]; - let labelPath = mch + ".label"; - let cflagPath = mch + ".custom"; - let namePath = mch + ".name"; - if (Theatre.DEBUG) console.log("found %s",k,mch,cflagPath,namePath); + let mch = k.match(/flags\.theatre\.emotes\.custom\d+/)[0]; + let name = mch.match(/custom\d+/)[0]; + let labelPath = mch + ".label"; + let cflagPath = mch + ".custom"; + let namePath = mch + ".name"; + if (Theatre.DEBUG) console.log("found %s", k, mch, cflagPath, namePath); // if label is both the formData as well as the object, reject the submission - let emoteProp = getProperty(this.object.data,mch); - let labelProp = null; - if (emoteProp) - labelProp = getProperty(this.object.data,labelPath); - - if ((!labelProp || labelProp == "") - && (!formData[labelPath] || formData[labelPath] == "")) { - console.log("ERROR: No label for custom emote defined!"); + let emoteProp = getProperty(this.object.data, mch); + let labelProp = null; + if (emoteProp) labelProp = getProperty(this.object.data, labelPath); + + if ((!labelProp || labelProp == "") && (!formData[labelPath] || formData[labelPath] == "")) { + console.log("ERROR: No label for custom emote defined!"); ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.BadCustomEmote")); - return false; + return false; } - if (!emoteProp || !getProperty(this.object.data,cflagPath)) - formData[cflagPath] = true; - if (!emoteProp || !getProperty(this.object.data,namePath)) - formData[namePath] = name; + if (!emoteProp || !getProperty(this.object.data, cflagPath)) formData[cflagPath] = true; + if (!emoteProp || !getProperty(this.object.data, namePath)) formData[namePath] = name; } // collect emote form updates + revised form updates - let configElement = this.element[0]; - let toDelete = configElement.querySelectorAll('.theatre-config-form-group[todelete="true"]'); - let emoteFormData = {}; - let revisedFormData = {}; + let configElement = this.element[0]; + let toDelete = configElement.querySelectorAll('.theatre-config-form-group[todelete="true"]'); + let emoteFormData = {}; + let revisedFormData = {}; for (let k in formData) { - let rem = false; - let isCustom = /custom\d+/.test(k); - let isEmote = /flags\.theatre\.emotes\./.test(k); + let rem = false; + let isCustom = /custom\d+/.test(k); + let isEmote = /flags\.theatre\.emotes\./.test(k); if (formData[k] && isCustom) { - let mch = k.match(/custom\d+/)[0]; + let mch = k.match(/custom\d+/)[0]; for (let d of toDelete) if (d.getAttribute("name") == mch) { - rem = true; + rem = true; break; // don't add it to our new object } } - if (!rem && isEmote) - emoteFormData[k] = formData[k]; - else if (!rem && !isEmote) - revisedFormData[k] = formData[k]; + if (!rem && isEmote) emoteFormData[k] = formData[k]; + else if (!rem && !isEmote) revisedFormData[k] = formData[k]; } // null out the entries if deleted in emote form, revised simply does not have any updates // to deleted entries for (let elem of toDelete) { - let name = elem.getAttribute("name"); - emoteFormData[`flags.theatre.emotes.${name}`] = null; + let name = elem.getAttribute("name"); + emoteFormData[`flags.theatre.emotes.${name}`] = null; } - return {emoteFormData: emoteFormData, revisedFormData: revisedFormData}; + return { emoteFormData: emoteFormData, revisedFormData: revisedFormData }; } /** * Given the formdata, check the levels in the given html element that have data-edit * and add their values to the formData update * - * @param formData (Object) : An object representing the formData that will be used to update the Entity. + * @param formData (Object) : An object representing the formData that will be used to update the Entity. * * @return Object : An object represeting the formData, but updated with new entries to be updated. */ _processUpdateLabels(formData) { - let html = this.element[0]; + let html = this.element[0]; - let dataLabels = html.querySelectorAll('label[data-edit]'); + let dataLabels = html.querySelectorAll("label[data-edit]"); for (let label of dataLabels) { - let target = label.getAttribute("data-edit"); - formData[target] = label.textContent; + let target = label.getAttribute("data-edit"); + formData[target] = label.textContent; } - return formData; + return formData; } - /** - * Implement the _updateObject method as required by the parent class spec - * This defines how to update the subject of the form when the form is submitted + /** + * Implement the _updateObject method as required by the parent class spec + * This defines how to update the subject of the form when the form is submitted * - * @param event (Object) : event that triggered this update ? - * @param formData (Object) : An object representing the formData that will be used to update the Entity. + * @param event (Object) : event that triggered this update ? + * @param formData (Object) : An object representing the formData that will be used to update the Entity. * - * @private - */ - async _updateObject(event, formData) { - formData["_id"] = this.object._id; + * @private + */ + async _updateObject(event, formData) { + formData["_id"] = this.object._id; // if our baseinsert value was updated.. - if (Theatre.DEBUG) console.log(formData); - let insertDirty = false; - let baseInsert = formData["flags.theatre.baseinsert"]; - let optAlign = formData["flags.theatre.optalign"]; - let name = formData["flags.theatre.name"]; - let newBaseInsert = this.object.data.flags.theatre.baseinsert || (this.object.img ? this.object.img : "icons/mystery-man.png"); - let newName = this.object.data.flags.theatre.name || this.object.data.name; - let newAlign = this.object.data.flags.theatre.optalign || "top"; + if (Theatre.DEBUG) console.log(formData); + let insertDirty = false; + let baseInsert = formData["flags.theatre.baseinsert"]; + let optAlign = formData["flags.theatre.optalign"]; + let name = formData["flags.theatre.name"]; + let newBaseInsert = this.object.data.flags.theatre.baseinsert || (this.object.img ? this.object.img : "icons/mystery-man.png"); + let newName = this.object.data.flags.theatre.name || this.object.data.name; + let newAlign = this.object.data.flags.theatre.optalign || "top"; // update Navbar of the corresponding ID - let theatreId = `theatre-${this.object.data._id}`; - let navItem = Theatre.instance.getNavItemById(theatreId); - let cImg = Theatre.instance.getTheatreCoverPortrait(); + let theatreId = `theatre-${this.object.data._id}`; + let navItem = Theatre.instance.getNavItemById(theatreId); + let cImg = Theatre.instance.getTheatreCoverPortrait(); if (baseInsert != this.object.data.flags.theatre.baseinsert) { - if (Theatre.DEBUG) console.log("baseinsert changed!"); - insertDirty = true; - newBaseInsert = (baseInsert == "" ? (this.object.img ? this.object.img : "icons/mystery-man.png") : baseInsert); + if (Theatre.DEBUG) console.log("baseinsert changed!"); + insertDirty = true; + newBaseInsert = baseInsert == "" ? (this.object.img ? this.object.img : "icons/mystery-man.png") : baseInsert; if (navItem) { - navItem.setAttribute("src",newBaseInsert); - cImg.setAttribute("src",newBaseInsert); + navItem.setAttribute("src", newBaseInsert); + cImg.setAttribute("src", newBaseInsert); } } if (optAlign != this.object.data.flags.theatre.optalign) { - if (Theatre.DEBUG) console.log("optalign changed!"); - insertDirty = true; - newAlign = (optAlign == "" ? "top" : optAlign) - if (navItem) - navItem.setAttribute("optalign",newAlign); + if (Theatre.DEBUG) console.log("optalign changed!"); + insertDirty = true; + newAlign = optAlign == "" ? "top" : optAlign; + if (navItem) navItem.setAttribute("optalign", newAlign); } if (name != this.object.data.flags.theatre.name) { - if (Theatre.DEBUG) console.log("name changed!"); - insertDirty = true; - newName = (name == "" ? this.object.data.name : name); + if (Theatre.DEBUG) console.log("name changed!"); + insertDirty = true; + newName = name == "" ? this.object.data.name : name; if (navItem) { - navItem.setAttribute("name",newName); - navItem.setAttribute("title",newName+(newName == this.object.data.name ? "" : ` (${this.object.data.name})`)); + navItem.setAttribute("name", newName); + navItem.setAttribute("title", newName + (newName == this.object.data.name ? "" : ` (${this.object.data.name})`)); } } // Add label information to update if it has data-edit - formData = this._processUpdateLabels(formData); + formData = this._processUpdateLabels(formData); // Verify custom emotes if we have any let resForms = this._verifyCustomEmotes(formData); - if (!resForms) return; - if (Theatre.DEBUG) console.log("Form data AFTER verification: ",resForms); - let revisedFormData = resForms.revisedFormData; - let emoteFormData = resForms.emoteFormData; + if (!resForms) return; + if (Theatre.DEBUG) console.log("Form data AFTER verification: ", resForms); + let revisedFormData = resForms.revisedFormData; + let emoteFormData = resForms.emoteFormData; // check all image resources, if they differ the actor's, we need to replace the texture, and then tell all other clients to do so as well! - //let inserts = formData.filter((e,k) => {return k.endsWith("insert") || k.endsWith("baseinsert")}); - let insert = Theatre.instance.getInsertById(theatreId); - let container = (insert ? insert.dockContainer : null); - let app = Theatre.instance.pixiCTX; - let insertEmote = Theatre.instance._getEmoteFromInsert(insert); - let newSrcImg = null; - let imgSrcs = []; + //let inserts = formData.filter((e,k) => {return k.endsWith("insert") || k.endsWith("baseinsert")}); + let insert = Theatre.instance.getInsertById(theatreId); + let container = insert ? insert.dockContainer : null; + let app = Theatre.instance.pixiCTX; + let insertEmote = Theatre.instance._getEmoteFromInsert(insert); + let newSrcImg = null; + let imgSrcs = []; for (let k in formData) if (k.endsWith("insert") || k.endsWith("baseinsert")) { - let oldValue = getProperty(this.object.data,k); + let oldValue = getProperty(this.object.data, k); // if the old value does not exist, we will continue if (formData[k] != oldValue) { - let emote = k.match(/emotes\.[a-z0-9\-]+/); - if (emote) - emote = emote[0].replace(/emotes\./,""); - let resName = formData[k]; + let emote = k.match(/emotes\.[a-z0-9\-]+/); + if (emote) emote = emote[0].replace(/emotes\./, ""); + let resName = formData[k]; // A special case exists where the baseportrait is removed, and replaced with either // null or an empty string, we can set this value, but we need to change the re-render // behavior to take the sheet portrait or 'mystery man' image if (!resName || resName == "") { // try to restore baseinsert - let formBaseInsert = formData["flags.theatre.baseinsert"]; + let formBaseInsert = formData["flags.theatre.baseinsert"]; if (k.endsWith("insert") && !k.endsWith("baseinsert")) { - if (formBaseInsert && formBaseInsert != "") - resName = formBaseInsert; - else if (this.object.data.flags.theatre.baseinsert && this.object.data.flags.theatre.baseinsert != "") - resName = this.object.data.flags.theatre.baseinsert; - else - resName = (this.object.data.img ? this.object.data.img : "icons/mystery-man.png"); - } else - resName = (this.object.data.img ? this.object.data.img : "icons/mystery-man.png"); + if (formBaseInsert && formBaseInsert != "") resName = formBaseInsert; + else if (this.object.data.flags.theatre.baseinsert && this.object.data.flags.theatre.baseinsert != "") + resName = this.object.data.flags.theatre.baseinsert; + else resName = this.object.data.img ? this.object.data.img : "icons/mystery-man.png"; + } else resName = this.object.data.img ? this.object.data.img : "icons/mystery-man.png"; } // ensure resource exists - if (!await srcExists(resName)) { - console.log("ERROR: Path %s does not exist!",resName); + if (!(await srcExists(resName))) { + console.log("ERROR: Path %s does not exist!", resName); ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.BadFilepath") + `"${resName}"`); - return; + return; } // to prevent firing off X number of packets on a save submit - imgSrcs.push({imgpath: resName, resname: resName}); - if (insertEmote == emote || !emote) - newSrcImg = resName; + imgSrcs.push({ imgpath: resName, resname: resName }); + if (insertEmote == emote || !emote) newSrcImg = resName; } } // check for null'd emotes, push the objects up a level if one exists - const newData = mergeObject(this.object.data, emoteFormData, {inplace: false}); - let emMerge = newData.flags.theatre.emotes; - let nEmotes = {}; + const newData = mergeObject(this.object.data, emoteFormData, { inplace: false }); + let emMerge = newData.flags.theatre.emotes; + let nEmotes = {}; for (let emProp in emMerge) { - if (emMerge[emProp] == null) - continue; - nEmotes[emProp] = emMerge[emProp]; + if (emMerge[emProp] == null) continue; + nEmotes[emProp] = emMerge[emProp]; } // send the emote parent in bulk to get rid of unwanted children - revisedFormData["flags.theatre.emotes"] = nEmotes; - if (Theatre.DEBUG) console.log("Final Push Config update:",revisedFormData); - - this.object.update(revisedFormData).then((response)=>{ + revisedFormData["flags.theatre.emotes"] = nEmotes; + if (Theatre.DEBUG) console.log("Final Push Config update:", revisedFormData); + + this.object.update(revisedFormData).then((response) => { // perform texture updates if needed if (imgSrcs.length > 0) { // we know the active emote, thus all we need is the new source image - if (Theatre.DEBUG) console.log("sending imgSrcs for replaceAllTextures",imgSrcs); - Theatre.instance._AddAllTextureResources(imgSrcs,theatreId,insertEmote,newSrcImg, (loader,resources) => { - // if our emote is active and we're replacing the emote texture, or base is active, and we're replacing the base texture - if (Theatre.DEBUG) console.log("texture additions complete! ",newSrcImg, insertEmote); - - if (app - && container - && newSrcImg) { - if (Theatre.DEBUG) console.log("RE-RENDERING with NEW texture resource %s ",newSrcImg); - - let resName = "icons/myster-man.png"; - if (insert.emote - && this.object.data.flags.theatre.emotes[insert.emote].insert - && this.object.data.flags.theatre.emotes[insert.emote].insert != "") - resName = this.object.data.flags.theatre.emotes[insert.emote].insert; - else if (this.object.data.flags.theatre.baseinsert - && this.object.data.flags.theatre.baseinsert != "") - resName = this.object.data.flags.theatre.baseinsert; - else if (this.object.data.img && this.object.data.img != "") - resName = this.object.data.img; - - // bubble up dataum from the update - insert.optAlign = newAlign; - insert.name = newName; - insert.label.text = newName; - - Theatre.instance._clearPortraitContainer(theatreId); - Theatre.instance._setupPortraitContainer(theatreId,newAlign,newSrcImg,resources); - // re-attach label + typingBubble - insert.dockContainer.addChild(insert.label); - insert.dockContainer.addChild(insert.typingBubble); - - Theatre.instance._repositionInsertElements(insert); - - if (!Theatre.instance.rendering) - Theatre.instance._renderTheatre(performance.now()); - } - },false); + if (Theatre.DEBUG) console.log("sending imgSrcs for replaceAllTextures", imgSrcs); + Theatre.instance._AddAllTextureResources( + imgSrcs, + theatreId, + insertEmote, + newSrcImg, + (loader, resources) => { + // if our emote is active and we're replacing the emote texture, or base is active, and we're replacing the base texture + if (Theatre.DEBUG) console.log("texture additions complete! ", newSrcImg, insertEmote); + + if (app && container && newSrcImg) { + if (Theatre.DEBUG) console.log("RE-RENDERING with NEW texture resource %s ", newSrcImg); + + let resName = "icons/myster-man.png"; + if (insert.emote && this.object.data.flags.theatre.emotes[insert.emote].insert && this.object.data.flags.theatre.emotes[insert.emote].insert != "") + resName = this.object.data.flags.theatre.emotes[insert.emote].insert; + else if (this.object.data.flags.theatre.baseinsert && this.object.data.flags.theatre.baseinsert != "") + resName = this.object.data.flags.theatre.baseinsert; + else if (this.object.data.img && this.object.data.img != "") resName = this.object.data.img; + + // bubble up dataum from the update + insert.optAlign = newAlign; + insert.name = newName; + insert.label.text = newName; + + Theatre.instance._clearPortraitContainer(theatreId); + Theatre.instance._setupPortraitContainer(theatreId, newAlign, newSrcImg, resources); + // re-attach label + typingBubble + insert.dockContainer.addChild(insert.label); + insert.dockContainer.addChild(insert.typingBubble); + + Theatre.instance._repositionInsertElements(insert); + + if (!Theatre.instance.rendering) Theatre.instance._renderTheatre(performance.now()); + } + }, + false + ); // replaceAllTextureResources will have performed the render, and sent the needed // packets // mark it as 'clean' since we're handling the render here - insertDirty = false; + insertDirty = false; } // if the insert is dirty, clear and setup if (insertDirty && insert) { - if (Theatre.DEBUG) console.log("Insert is dirty, re-render it!"); + if (Theatre.DEBUG) console.log("Insert is dirty, re-render it!"); let resName = "icons/myster-man.png"; - if (insert.emote - && this.object.data.flags.theatre.emotes[insert.emote].insert - && this.object.data.flags.theatre.emotes[insert.emote].insert != "") - resName = this.object.data.flags.theatre.emotes[insert.emote].insert; - else if (this.object.data.flags.theatre.baseinsert - && this.object.data.flags.theatre.baseinsert != "") - resName = this.object.data.flags.theatre.baseinsert; - else if (this.object.data.img && this.object.data.img != "") - resName = this.object.data.img; + if (insert.emote && this.object.data.flags.theatre.emotes[insert.emote].insert && this.object.data.flags.theatre.emotes[insert.emote].insert != "") + resName = this.object.data.flags.theatre.emotes[insert.emote].insert; + else if (this.object.data.flags.theatre.baseinsert && this.object.data.flags.theatre.baseinsert != "") resName = this.object.data.flags.theatre.baseinsert; + else if (this.object.data.img && this.object.data.img != "") resName = this.object.data.img; // bubble up dataum from the update insert.optAlign = newAlign; - insert.name = newName; - insert.label.text = newName; + insert.name = newName; + insert.label.text = newName; - Theatre.instance._clearPortraitContainer(theatreId); - Theatre.instance._setupPortraitContainer(theatreId,newAlign,resName,PIXI.Loader.shared.resources); + Theatre.instance._clearPortraitContainer(theatreId); + Theatre.instance._setupPortraitContainer(theatreId, newAlign, resName, PIXI.Loader.shared.resources); // re-attach label + typingBubble - insert.dockContainer.addChild(insert.label); - insert.dockContainer.addChild(insert.typingBubble); + insert.dockContainer.addChild(insert.label); + insert.dockContainer.addChild(insert.typingBubble); - Theatre.instance._repositionInsertElements(insert); + Theatre.instance._repositionInsertElements(insert); - if (!Theatre.instance.rendering) - Theatre.instance._renderTheatre(performance.now()); + if (!Theatre.instance.rendering) Theatre.instance._renderTheatre(performance.now()); } - if (theatreId == Theatre.instance.speakingAs); - Theatre.instance.renderEmoteMenu(); - if (insertDirty) - Theatre.instance._sendSceneEvent("renderinsert",{insertid: theatreId}); - + if (theatreId == Theatre.instance.speakingAs); + Theatre.instance.renderEmoteMenu(); + if (insertDirty) Theatre.instance._sendSceneEvent("renderinsert", { insertid: theatreId }); }); - - - } + } /** * Adds a new Custom emote, constructing the HTML to be injected @@ -433,133 +400,132 @@ class TheatreActorConfig extends FormApplication { * @private */ _onAddEmoteLine(ev) { - if (Theatre.DEBUG) console.log("Add Emote Pressed!"); + if (Theatre.DEBUG) console.log("Add Emote Pressed!"); //ui.notifications.info(game.i18n.localize("Theatre.NotYet")); // We need to get a custom emote name for storage purposes, this is a running index from // 1-> MAXINT oh which the upper bound we don't account for, to get the correct custom // index to fill, we find all formGroups whose name starts with "custom" then when we // shave off the number, then we sort these numbers - let emoteContainer = ev.currentTarget.parentNode; - let formEmoteElems = emoteContainer.getElementsByClassName("theatre-config-form-group"); + let emoteContainer = ev.currentTarget.parentNode; + let formEmoteElems = emoteContainer.getElementsByClassName("theatre-config-form-group"); - let customElems = []; + let customElems = []; for (let elem of formEmoteElems) { - let eName = elem.getAttribute("name"); - if (eName && eName.startsWith("custom")) - customElems.push({sortidx: Number(eName.match(/\d+/)[0]),elem: elem}); + let eName = elem.getAttribute("name"); + if (eName && eName.startsWith("custom")) customElems.push({ sortidx: Number(eName.match(/\d+/)[0]), elem: elem }); } // we grab max index, we don't care about possible missing indexes from removed custom emotes // so we'll just leave them as gaps - customElems.sort((a,b)=>{return a.sortidx-b.sortidx}); - let customIdx = (customElems.length > 0 ? (customElems[customElems.length-1].sortidx+1) : 1); - + customElems.sort((a, b) => { + return a.sortidx - b.sortidx; + }); + let customIdx = customElems.length > 0 ? customElems[customElems.length - 1].sortidx + 1 : 1; - let customObjElems = []; + let customObjElems = []; for (let k in this.object.data.flags.theatre.emotes) { - let eName = k; - if (eName && eName.startsWith("custom")) - customObjElems.push({sortidx: Number(eName.match(/\d+/)[0]),elem: this.object.data.flags.theatre.emotes[k]}); + let eName = k; + if (eName && eName.startsWith("custom")) customObjElems.push({ sortidx: Number(eName.match(/\d+/)[0]), elem: this.object.data.flags.theatre.emotes[k] }); } // we grab max index, we don't care about possible missing indexes from removed custom emotes // so we'll just leave them as gaps - customObjElems.sort((a,b)=>{return a.sortidx-b.sortidx}); - let customObjIdx = (customObjElems.length > 0 ? (customObjElems[customObjElems.length-1].sortidx+1) : 1); - let customName = `custom${Math.max(customIdx,customObjIdx)}`; - - + customObjElems.sort((a, b) => { + return a.sortidx - b.sortidx; + }); + let customObjIdx = customObjElems.length > 0 ? customObjElems[customObjElems.length - 1].sortidx + 1 : 1; + let customName = `custom${Math.max(customIdx, customObjIdx)}`; // inject a new DOM element to the emote list right before our button - let formGroup = document.createElement("div"); - let emoteNameInput = document.createElement("input"); - let emoteIconHolder = document.createElement("div"); - let emoteIcon = document.createElement("img"); - let fileButton = document.createElement("button"); - let fileIcon = document.createElement("i"); - let fileInput = document.createElement("input"); - //let editEmoteButton = document.createElement("button"); - //let editEmoteIcon = document.createElement("i"); - - KHelpers.addClass(formGroup,"theatre-config-form-group"); - KHelpers.addClass(emoteIconHolder,"theatre-emote-icon"); - KHelpers.addClass(emoteIconHolder,"file-picker"); - KHelpers.addClass(emoteIcon,"customicon"); - KHelpers.addClass(fileButton,"file-picker"); - KHelpers.addClass(fileIcon,"fas"); - KHelpers.addClass(fileIcon,"fa-file-import"); - KHelpers.addClass(fileIcon,"fa-fw"); - KHelpers.addClass(fileInput,"image"); - //KHelpers.addClass(editEmoteButton,"theatre-config-btn-edit-emote"); - //KHelpers.addClass(editEmoteIcon,"fas"); - //KHelpers.addClass(editEmoteIcon,"fa-sliders-h"); - - formGroup.setAttribute("name",customName); - - emoteNameInput.setAttribute("type","text"); - emoteNameInput.setAttribute("name",`flags.theatre.emotes.${customName}.label`); - emoteNameInput.setAttribute("data-dtype","String"); - emoteNameInput.setAttribute("placeholder",game.i18n.localize("Theatre.UI.Config.CustomEmotePlaceholder")); - emoteNameInput.value = game.i18n.localize("Theatre.UI.Config.CustomEmotePlaceholder"); - emoteNameInput.addEventListener("focusout",this._onCustomLabelInputFocusOut.bind(this)); - - fileButton.setAttribute("type","button"); - fileButton.setAttribute("data-type","image"); - fileButton.setAttribute("data-target",`flags.theatre.emotes.${customName}.insert`); - fileButton.setAttribute("title","Browse Files"); - fileButton.setAttribute("tabindex","-1"); - - emoteIcon.setAttribute("data-edit",`flags.theatre.emotes.${customName}.image`); - emoteIcon.setAttribute("src",Theatre.ICONLIB + "/blank.png"); - emoteIcon.setAttribute("title",game.i18n.localize("Theatre.UI.Title.ChooseEmoteIcon")); - - //emoteIcon.setAttribute("src",`flags.theatre.emotes.${customName}.image`); - - fileInput.setAttribute("type","text"); - fileInput.setAttribute("name",`flags.theatre.emotes.${customName}.insert`); - fileInput.setAttribute("data-dtype","String"); - fileInput.setAttribute("placeholder",game.i18n.localize("Theatre.UI.Config.PathPlaceholder")); - - //editEmoteButton.setAttribute("type","button"); - //editEmoteButton.setAttribute("name", customName); - //editEmoteButton.setAttribute("title",game.i18n.localize("Theatre.UI.Config.ConfigureEmote")); + let formGroup = document.createElement("div"); + let emoteNameInput = document.createElement("input"); + let emoteIconHolder = document.createElement("div"); + let emoteIcon = document.createElement("img"); + let fileButton = document.createElement("button"); + let fileIcon = document.createElement("i"); + let fileInput = document.createElement("input"); + //let editEmoteButton = document.createElement("button"); + //let editEmoteIcon = document.createElement("i"); + + KHelpers.addClass(formGroup, "theatre-config-form-group"); + KHelpers.addClass(emoteIconHolder, "theatre-emote-icon"); + KHelpers.addClass(emoteIconHolder, "file-picker"); + KHelpers.addClass(emoteIcon, "customicon"); + KHelpers.addClass(fileButton, "file-picker"); + KHelpers.addClass(fileIcon, "fas"); + KHelpers.addClass(fileIcon, "fa-file-import"); + KHelpers.addClass(fileIcon, "fa-fw"); + KHelpers.addClass(fileInput, "image"); + //KHelpers.addClass(editEmoteButton,"theatre-config-btn-edit-emote"); + //KHelpers.addClass(editEmoteIcon,"fas"); + //KHelpers.addClass(editEmoteIcon,"fa-sliders-h"); + + formGroup.setAttribute("name", customName); + + emoteNameInput.setAttribute("type", "text"); + emoteNameInput.setAttribute("name", `flags.theatre.emotes.${customName}.label`); + emoteNameInput.setAttribute("data-dtype", "String"); + emoteNameInput.setAttribute("placeholder", game.i18n.localize("Theatre.UI.Config.CustomEmotePlaceholder")); + emoteNameInput.value = game.i18n.localize("Theatre.UI.Config.CustomEmotePlaceholder"); + emoteNameInput.addEventListener("focusout", this._onCustomLabelInputFocusOut.bind(this)); + + fileButton.setAttribute("type", "button"); + fileButton.setAttribute("data-type", "image"); + fileButton.setAttribute("data-target", `flags.theatre.emotes.${customName}.insert`); + fileButton.setAttribute("title", "Browse Files"); + fileButton.setAttribute("tabindex", "-1"); + + emoteIcon.setAttribute("data-edit", `flags.theatre.emotes.${customName}.image`); + emoteIcon.setAttribute("src", Theatre.ICONLIB + "/blank.png"); + emoteIcon.setAttribute("title", game.i18n.localize("Theatre.UI.Title.ChooseEmoteIcon")); + + //emoteIcon.setAttribute("src",`flags.theatre.emotes.${customName}.image`); + + fileInput.setAttribute("type", "text"); + fileInput.setAttribute("name", `flags.theatre.emotes.${customName}.insert`); + fileInput.setAttribute("data-dtype", "String"); + fileInput.setAttribute("placeholder", game.i18n.localize("Theatre.UI.Config.PathPlaceholder")); + + //editEmoteButton.setAttribute("type","button"); + //editEmoteButton.setAttribute("name", customName); + //editEmoteButton.setAttribute("title",game.i18n.localize("Theatre.UI.Config.ConfigureEmote")); // assemble - emoteIconHolder.appendChild(emoteIcon); - //editEmoteButton.appendChild(editEmoteIcon); - fileButton.appendChild(fileIcon); + emoteIconHolder.appendChild(emoteIcon); + //editEmoteButton.appendChild(editEmoteIcon); + fileButton.appendChild(fileIcon); formGroup.appendChild(emoteNameInput); formGroup.appendChild(emoteIconHolder); formGroup.appendChild(fileButton); formGroup.appendChild(fileInput); - //formGroup.appendChild(editEmoteButton); + //formGroup.appendChild(editEmoteButton); - KHelpers.insertBefore(formGroup,ev.currentTarget); - this.activateListeners($(formGroup)); + KHelpers.insertBefore(formGroup, ev.currentTarget); + this.activateListeners($(formGroup)); // focus - emoteNameInput.focus(); + emoteNameInput.focus(); } - /** - * Handle changing customEmote image by + /** + * Handle changing customEmote image by * * @param ev (Event) triggered event * - * @private - */ - _onCustomIconImage(ev) { - let target = ev.currentTarget; - new FilePicker({ - type: "image", - current: target.getAttribute("src"), - callback: path => { - target.src = path; - }, - top: this.position.top + 40, - left: this.position.left + 10 - }).browse(target.getAttribute("src")); - } + * @private + */ + _onCustomIconImage(ev) { + let target = ev.currentTarget; + new FilePicker({ + type: "image", + current: target.getAttribute("src"), + callback: (path) => { + target.src = path; + }, + top: this.position.top + 40, + left: this.position.left + 10, + }).browse(target.getAttribute("src")); + } /** * Handle click event for the custom name label to allow it to be editable @@ -570,19 +536,19 @@ class TheatreActorConfig extends FormApplication { */ _onCustomLabelClick(ev) { // replace the label with an input box - ev.stopPropagation(); - let inputLabel = document.createElement("input"); - inputLabel.setAttribute("type","text"); - inputLabel.setAttribute("name",`flags.theatre.emotes.${ev.currentTarget.parentNode.getAttribute("name")}.label`); - inputLabel.setAttribute("data-dtype","String"); - inputLabel.setAttribute("placeholder",game.i18n.localize("Theatre.UI.Config.CustomEmotePlaceholder")); - inputLabel.setAttribute("value",ev.currentTarget.textContent); - inputLabel.addEventListener("focusout",this._onCustomLabelInputFocusOut.bind(this)); - KHelpers.insertBefore(inputLabel,ev.currentTarget); - inputLabel.select(); - inputLabel.focus(); + ev.stopPropagation(); + let inputLabel = document.createElement("input"); + inputLabel.setAttribute("type", "text"); + inputLabel.setAttribute("name", `flags.theatre.emotes.${ev.currentTarget.parentNode.getAttribute("name")}.label`); + inputLabel.setAttribute("data-dtype", "String"); + inputLabel.setAttribute("placeholder", game.i18n.localize("Theatre.UI.Config.CustomEmotePlaceholder")); + inputLabel.setAttribute("value", ev.currentTarget.textContent); + inputLabel.addEventListener("focusout", this._onCustomLabelInputFocusOut.bind(this)); + KHelpers.insertBefore(inputLabel, ev.currentTarget); + inputLabel.select(); + inputLabel.focus(); // replace - ev.currentTarget.parentNode.removeChild(ev.currentTarget); + ev.currentTarget.parentNode.removeChild(ev.currentTarget); } /** @@ -594,8 +560,8 @@ class TheatreActorConfig extends FormApplication { */ _onCustomLabelMouseEnter(ev) { // show dock - let dock = ev.currentTarget.getElementsByClassName("theatre-config-emote-label-dock")[0]; - dock.style.display = "flex"; + let dock = ev.currentTarget.getElementsByClassName("theatre-config-emote-label-dock")[0]; + dock.style.display = "flex"; } /** @@ -607,8 +573,8 @@ class TheatreActorConfig extends FormApplication { */ _onCustomLabelMouseLeave(ev) { // hide dock - let dock = ev.currentTarget.getElementsByClassName("theatre-config-emote-label-dock")[0]; - dock.style.display = "none"; + let dock = ev.currentTarget.getElementsByClassName("theatre-config-emote-label-dock")[0]; + dock.style.display = "none"; } /** @@ -620,27 +586,27 @@ class TheatreActorConfig extends FormApplication { */ _onCustomLabelInputFocusOut(ev) { // re-build dock + label - let label = document.createElement("label"); - let dock = document.createElement("div"); - let deleteIcon = document.createElement("i"); - KHelpers.addClass(label,"theatre-config-emote-label"); - KHelpers.addClass(label,"customlabel"); - KHelpers.addClass(dock,"theatre-config-emote-label-dock"); - KHelpers.addClass(deleteIcon,"fas"); - KHelpers.addClass(deleteIcon,"fa-trash"); - - label.textContent = ev.currentTarget.value; - - label.setAttribute("title",game.i18n.localize("Theatre.UI.Title.ChooseEmoteName")); - label.setAttribute("data-edit",`flags.theatre.emotes.${ev.currentTarget.parentNode.getAttribute("name")}.label`); - dock.setAttribute("title",game.i18n.localize("Theatre.UI.Title.DeleteCustomEmote")); - - dock.appendChild(deleteIcon); - label.appendChild(dock); - KHelpers.insertBefore(label,ev.currentTarget); - this._setupCustomLabelEvents(label); + let label = document.createElement("label"); + let dock = document.createElement("div"); + let deleteIcon = document.createElement("i"); + KHelpers.addClass(label, "theatre-config-emote-label"); + KHelpers.addClass(label, "customlabel"); + KHelpers.addClass(dock, "theatre-config-emote-label-dock"); + KHelpers.addClass(deleteIcon, "fas"); + KHelpers.addClass(deleteIcon, "fa-trash"); + + label.textContent = ev.currentTarget.value; + + label.setAttribute("title", game.i18n.localize("Theatre.UI.Title.ChooseEmoteName")); + label.setAttribute("data-edit", `flags.theatre.emotes.${ev.currentTarget.parentNode.getAttribute("name")}.label`); + dock.setAttribute("title", game.i18n.localize("Theatre.UI.Title.DeleteCustomEmote")); + + dock.appendChild(deleteIcon); + label.appendChild(dock); + KHelpers.insertBefore(label, ev.currentTarget); + this._setupCustomLabelEvents(label); // replace - ev.currentTarget.parentNode.removeChild(ev.currentTarget); + ev.currentTarget.parentNode.removeChild(ev.currentTarget); } /** @@ -653,14 +619,14 @@ class TheatreActorConfig extends FormApplication { _onCustomLabelDockClick(ev) { // delete custom emote // mark the form group as 'to be deleted' as a rider on our update call - let formGroup = KHelpers.seekParentClass(ev.currentTarget,"theatre-config-form-group",5); + let formGroup = KHelpers.seekParentClass(ev.currentTarget, "theatre-config-form-group", 5); if (!formGroup) return; - formGroup.setAttribute("todelete",true); + formGroup.setAttribute("todelete", true); formGroup.style.left = "20px"; formGroup.style.transform = "scale(0.75)"; formGroup.style.opacity = "0.25"; - ev.stopPropagation(); - formGroup.addEventListener("click",this._onUndoDockDelete.bind(this)); + ev.stopPropagation(); + formGroup.addEventListener("click", this._onUndoDockDelete.bind(this)); } /** @@ -671,9 +637,9 @@ class TheatreActorConfig extends FormApplication { * @private */ _onUndoDockDelete(ev) { - if (Theatre.DEBUG) console.log("undo delete!"); - ev.stopPropagation(); - ev.currentTarget.removeAttribute("todelete"); + if (Theatre.DEBUG) console.log("undo delete!"); + ev.stopPropagation(); + ev.currentTarget.removeAttribute("todelete"); ev.currentTarget.style.left = "0"; ev.currentTarget.style.transform = "scale(1)"; ev.currentTarget.style.opacity = "1"; @@ -687,11 +653,11 @@ class TheatreActorConfig extends FormApplication { * @private */ _setupCustomLabelEvents(label) { - label.addEventListener("click",this._onCustomLabelClick.bind(this)); - label.addEventListener("mouseenter",this._onCustomLabelMouseEnter.bind(this)); - label.addEventListener("mouseleave",this._onCustomLabelMouseLeave.bind(this)); - let dock = label.getElementsByClassName("theatre-config-emote-label-dock")[0]; - dock.addEventListener("click",this._onCustomLabelDockClick.bind(this)); + label.addEventListener("click", this._onCustomLabelClick.bind(this)); + label.addEventListener("mouseenter", this._onCustomLabelMouseEnter.bind(this)); + label.addEventListener("mouseleave", this._onCustomLabelMouseLeave.bind(this)); + let dock = label.getElementsByClassName("theatre-config-emote-label-dock")[0]; + dock.addEventListener("click", this._onCustomLabelDockClick.bind(this)); } /** @@ -702,10 +668,7 @@ class TheatreActorConfig extends FormApplication { * @private */ _onEditEmoteLine(ev) { - if (Theatre.DEBUG) console.log("Emote config pressed for %s!",ev.currentTarget.getAttribute("name")); + if (Theatre.DEBUG) console.log("Emote config pressed for %s!", ev.currentTarget.getAttribute("name")); ui.notifications.info(game.i18n.localize("Theatre.NotYet")); } - - } - diff --git a/app/js/theatre_main.js b/app/js/theatre_main.js index af78d64..0fe69f1 100644 --- a/app/js/theatre_main.js +++ b/app/js/theatre_main.js @@ -29,911 +29,855 @@ * * ============================================================ */ - var KHelpers = (function() { - function hasClass(el, className) { - return el.classList - ? el.classList.contains(className) - : new RegExp("\\b" + className + "\\b").test(el.className); - } - - function addClass(el, className) { - if (el.classList) el.classList.add(className); - else if (!KHelpers.hasClass(el, className)) el.className += " " + className; - } - - function removeClass(el, className) { - if (el.classList) el.classList.remove(className); - else - el.className = el.className.replace( - new RegExp("\\b" + className + "\\b", "g"), - "" - ); - } - - function offset(el) { - var rect = el.getBoundingClientRect(), - scrollLeft = window.pageXOffset || document.documentElement.scrollLeft, - scrollTop = window.pageYOffset || document.documentElement.scrollTop; - return { top: rect.top + scrollTop, left: rect.left + scrollLeft }; - } - - function style(el) { - return el.currentStyle || window.getComputedStyle(el); - } - function insertAfter(el, referenceNode) { - referenceNode.parentNode.insertBefore(el, referenceNode.nextSibling); - } - function insertBefore(el, referenceNode) { - referenceNode.parentNode.insertBefore(el, referenceNode); - } - - /** - * Helper to grab a parent class via CSS ClassName - * - * @param elem (HTMLElement) : the element to start from. - * @param cls (String) : The class name to search for. - * @param depth (Number) : The maximum height/depth to look up. - * @returns (HTMLElement) : the parent class if found, or null if - * no such parent exists within the specified - * depth. - */ - - function seekParentClass(elem, cls, depth) { - depth = depth || 5; - let el = elem; - let targ = null; - for (let i = 0; i < depth; ++i) { - if (!el) break; - if (KHelpers.hasClass(el, cls)) { - targ = el; - break; - } else el = el.parentNode; - } - return targ; - } - - return { - hasClass: hasClass, - addClass: addClass, - removeClass: removeClass, - offset: offset, - style: style, - insertAfter: insertAfter, - insertBefore: insertBefore, - seekParentClass: seekParentClass - }; +var KHelpers = (function () { + function hasClass(el, className) { + return el.classList ? el.classList.contains(className) : new RegExp("\\b" + className + "\\b").test(el.className); + } + + function addClass(el, className) { + if (el.classList) el.classList.add(className); + else if (!KHelpers.hasClass(el, className)) el.className += " " + className; + } + + function removeClass(el, className) { + if (el.classList) el.classList.remove(className); + else el.className = el.className.replace(new RegExp("\\b" + className + "\\b", "g"), ""); + } + + function offset(el) { + var rect = el.getBoundingClientRect(), + scrollLeft = window.pageXOffset || document.documentElement.scrollLeft, + scrollTop = window.pageYOffset || document.documentElement.scrollTop; + return { top: rect.top + scrollTop, left: rect.left + scrollLeft }; + } + + function style(el) { + return el.currentStyle || window.getComputedStyle(el); + } + function insertAfter(el, referenceNode) { + referenceNode.parentNode.insertBefore(el, referenceNode.nextSibling); + } + function insertBefore(el, referenceNode) { + referenceNode.parentNode.insertBefore(el, referenceNode); + } + + /** + * Helper to grab a parent class via CSS ClassName + * + * @param elem (HTMLElement) : the element to start from. + * @param cls (String) : The class name to search for. + * @param depth (Number) : The maximum height/depth to look up. + * @returns (HTMLElement) : the parent class if found, or null if + * no such parent exists within the specified + * depth. + */ + + function seekParentClass(elem, cls, depth) { + depth = depth || 5; + let el = elem; + let targ = null; + for (let i = 0; i < depth; ++i) { + if (!el) break; + if (KHelpers.hasClass(el, cls)) { + targ = el; + break; + } else el = el.parentNode; + } + return targ; + } + + return { + hasClass: hasClass, + addClass: addClass, + removeClass: removeClass, + offset: offset, + style: style, + insertAfter: insertAfter, + insertBefore: insertBefore, + seekParentClass: seekParentClass, + }; })(); /** * Concat helper */ -Handlebars.registerHelper("cat", function(arg1, arg2, hash) { - let res = String(arg1) + String(arg2); - return res; +Handlebars.registerHelper("cat", function (arg1, arg2, hash) { + let res = String(arg1) + String(arg2); + return res; }); /** * Given a string representing a property, resolve it as an actual property, * this is meant to be used in subexpressions rather than a final target */ -Handlebars.registerHelper("resprop", function(propPath, hash) { - let prop = getProperty(hash.data.root, propPath); - return prop; +Handlebars.registerHelper("resprop", function (propPath, hash) { + let prop = getProperty(hash.data.root, propPath); + return prop; }); /** * Hook in on Actorsheet's Header buttons + context menus */ - Hooks.on("getActorSheetHeaderButtons",(app,buttons)=>{ - if (!game.user.isGM && game.settings.get("theatre", "gmOnly")) return; - - let theatreButtons = [] - if (app.object.isOwner) { - // only prototype actors - if (!app.object.token) { - - theatreButtons.push({ - label: "Theatre.UI.Config.Theatre", - class: "configure-theatre", - icon: "fas fa-user-edit", - onclick: ev => Theatre.onConfigureInsert(ev, app.object.sheet) - }) - - } - theatreButtons.push({ - label: Theatre.isActorStaged(app.object.data) ? "Theatre.UI.Config.RemoveFromStage" : "Theatre.UI.Config.AddToStage", - class: "add-to-theatre-navbar", - icon: "fas fa-theater-masks", - onclick: ev => { - Theatre.onAddToNavBar(ev, app.object.sheet); - } - }) - } - buttons.unshift(...theatreButtons) +Hooks.on("getActorSheetHeaderButtons", (app, buttons) => { + if (!game.user.isGM && game.settings.get("theatre", "gmOnly")) return; + + let theatreButtons = []; + if (app.object.isOwner) { + // only prototype actors + if (!app.object.token) { + theatreButtons.push({ + label: "Theatre.UI.Config.Theatre", + class: "configure-theatre", + icon: "fas fa-user-edit", + onclick: (ev) => Theatre.onConfigureInsert(ev, app.object.sheet), + }); + } + theatreButtons.push({ + label: Theatre.isActorStaged(app.object.data) ? "Theatre.UI.Config.RemoveFromStage" : "Theatre.UI.Config.AddToStage", + class: "add-to-theatre-navbar", + icon: "fas fa-theater-masks", + onclick: (ev) => { + Theatre.onAddToNavBar(ev, app.object.sheet); + }, + }); + } + buttons.unshift(...theatreButtons); }); /** * Sidebar collapse hook */ -Hooks.on("sidebarCollapse", function(a, collapsed) { - // If theatre isn't even ready, then just no - if (!Theatre.instance) return; - - if (Theatre.DEBUG) console.log("collapse? : ", a, collapsed); - let sideBar = document.getElementById("sidebar"); - let primeBar = document.getElementById("theatre-prime-bar"); - let secondBar = document.getElementById("theatre-second-bar"); - - if (collapsed) { - // set width to 100% - Theatre.instance.theatreBar.style.width = "100%"; - Theatre.instance.theatreNarrator.style.width = "100%"; - } else { - // set width to sidebar offset size - Theatre.instance.theatreBar.style.width = `calc(100% - ${sideBar.offsetWidth + - 2}px)`; - Theatre.instance.theatreNarrator.style.width = `calc(100% - ${sideBar.offsetWidth + - 2}px)`; - if (Theatre.instance._getTextBoxes().length == 2) { - let dualWidth = Math.min( - Math.floor(Theatre.instance.theatreBar.offsetWidth / 2), - 650 - ); - primeBar.style.width = dualWidth + "px"; - secondBar.style.width = dualWidth + "px"; - secondBar.style.left = `calc(100% - ${dualWidth}px)`; - } - } - Theatre.instance.theatreEmoteMenu.style.top = `${Theatre.instance - .theatreControls.offsetTop - 410}px`; - - if (Theatre.instance.reorderTOId) - window.clearTimeout(Theatre.instance.reorderTOId); - - Theatre.instance.reorderTOId = window.setTimeout(() => { - Theatre.reorderInserts(); - Theatre.instance.reorderTOId = null; - }, 250); +Hooks.on("sidebarCollapse", function (a, collapsed) { + // If theatre isn't even ready, then just no + if (!Theatre.instance) return; + + if (Theatre.DEBUG) console.log("collapse? : ", a, collapsed); + let sideBar = document.getElementById("sidebar"); + let primeBar = document.getElementById("theatre-prime-bar"); + let secondBar = document.getElementById("theatre-second-bar"); + + if (collapsed) { + // set width to 100% + Theatre.instance.theatreBar.style.width = "100%"; + Theatre.instance.theatreNarrator.style.width = "100%"; + } else { + // set width to sidebar offset size + Theatre.instance.theatreBar.style.width = `calc(100% - ${sideBar.offsetWidth + 2}px)`; + Theatre.instance.theatreNarrator.style.width = `calc(100% - ${sideBar.offsetWidth + 2}px)`; + if (Theatre.instance._getTextBoxes().length == 2) { + let dualWidth = Math.min(Math.floor(Theatre.instance.theatreBar.offsetWidth / 2), 650); + primeBar.style.width = dualWidth + "px"; + secondBar.style.width = dualWidth + "px"; + secondBar.style.left = `calc(100% - ${dualWidth}px)`; + } + } + Theatre.instance.theatreEmoteMenu.style.top = `${Theatre.instance.theatreControls.offsetTop - 410}px`; + + if (Theatre.instance.reorderTOId) window.clearTimeout(Theatre.instance.reorderTOId); + + Theatre.instance.reorderTOId = window.setTimeout(() => { + Theatre.reorderInserts(); + Theatre.instance.reorderTOId = null; + }, 250); }); /** * Handle combat start */ -Hooks.on("createCombat", function() { - // If theatre isn't even ready, then just no - if (!Theatre.instance) return; - - if ( - !!game.combats.active && - game.combats.active.round == 0 && - Theatre.instance.isSuppressed - ) { - if (Theatre.DEBUG) console.log("COMBAT CREATED"); - // if suppressed, change opacity to 0.05 - //Theatre.instance.theatreGroup.style.opacity = "0.05"; - Theatre.instance.theatreDock.style.opacity = "1"; - Theatre.instance.theatreBar.style.opacity = "1"; - Theatre.instance.theatreNarrator.style.opacity = "1"; - } +Hooks.on("createCombat", function () { + // If theatre isn't even ready, then just no + if (!Theatre.instance) return; + + if (!!game.combats.active && game.combats.active.round == 0 && Theatre.instance.isSuppressed) { + if (Theatre.DEBUG) console.log("COMBAT CREATED"); + // if suppressed, change opacity to 0.05 + //Theatre.instance.theatreGroup.style.opacity = "0.05"; + Theatre.instance.theatreDock.style.opacity = "1"; + Theatre.instance.theatreBar.style.opacity = "1"; + Theatre.instance.theatreNarrator.style.opacity = "1"; + } }); /** * Handle combat end */ -Hooks.on("deleteCombat", function() { - // If theatre isn't even ready, then just no - if (!Theatre.instance) return; - - if (!game.combats.active && Theatre.instance.isSuppressed) { - if (Theatre.DEBUG) console.log("COMBAT DELETED"); - // if suppressed, change opacity to 0.25 - //Theatre.instance.theatreGroup.style.opacity = "0.25"; - Theatre.instance.theatreDock.style.opacity = "0.20"; - Theatre.instance.theatreBar.style.opacity = "0.20"; - Theatre.instance.theatreNarrator.style.opacity = "0.20"; - } +Hooks.on("deleteCombat", function () { + // If theatre isn't even ready, then just no + if (!Theatre.instance) return; + + if (!game.combats.active && Theatre.instance.isSuppressed) { + if (Theatre.DEBUG) console.log("COMBAT DELETED"); + // if suppressed, change opacity to 0.25 + //Theatre.instance.theatreGroup.style.opacity = "0.25"; + Theatre.instance.theatreDock.style.opacity = "0.20"; + Theatre.instance.theatreBar.style.opacity = "0.20"; + Theatre.instance.theatreNarrator.style.opacity = "0.20"; + } }); /** * Pre-process chat message to set 'speaking as' to correspond * to our 'speaking as' */ -Hooks.on("preCreateChatMessage", function(chatMessage) { - let chatData = { - speaker:{} - }; - if (Theatre.DEBUG) console.log("preCreateChatMessage", chatMessage.data); - // If theatre isn't even ready, then just no - if (!Theatre.instance) return; - - // make the message OOC if needed - if (!chatMessage.data.roll && $(theatre.theatreChatCover).hasClass("theatre-control-chat-cover-ooc")) { - const user = game.users.get(chatMessage.data.user.id); - chatData.speaker.alias = user.data.name; - chatData.speaker.actor = null; - chatData.speaker.scene = null; - chatData.type = CONST.CHAT_MESSAGE_TYPES.OOC; - - chatMessage.data.update(chatData); - return; - } - - if ( - !chatMessage.data.roll && - Theatre.instance.speakingAs && - Theatre.instance.usersTyping[chatMessage.data.user.id] - ) { - let theatreId = Theatre.instance.usersTyping[chatMessage.data.user.id].theatreId; - let insert = Theatre.instance.getInsertById(theatreId); - let actorId = theatreId.replace("theatre-", ""); - let actor = game.actors.get(actorId) || null; - if (Theatre.DEBUG) console.log("speakingAs %s", theatreId); - - if (insert && chatMessage.data.speaker) { - let label = Theatre.instance._getLabelFromInsert(insert); - let name = label.text; - let theatreColor = Theatre.instance.getPlayerFlashColor( - chatMessage.data.user.id, - insert.textColor - ); - if (Theatre.DEBUG) console.log("name is %s", name); - chatData.speaker.alias = name; - chatData.speaker.actor = null; - chatData.speaker.scene = null; - //chatData.flags.theatreColor = theatreColor; - chatData.type = CONST.CHAT_MESSAGE_TYPES.IC; - // if delay emote is active - if ( - Theatre.instance.isDelayEmote && - Theatre.instance.delayedSentState == 1 - ) { - if (Theatre.DEBUG) - console.log("setting emote now! as %s", insert.emote); - Theatre.instance.delayedSentState = 2; - Theatre.instance.setUserEmote( - game.user._id, - theatreId, - "emote", - insert.emote, - false - ); - Theatre.instance.delayedSentState = 0; - } - } else if (insert) { - let label = Theatre.instance._getLabelFromInsert(insert); - let name = label.text; - let theatreColor = Theatre.instance.getPlayerFlashColor( - chatData.user, - insert.textColor - ); - chatData.speaker = {}; - chatData.speaker.alias = name; - chatData.speaker.actor = null; - chatData.speaker.scene = null; - //chatData.flags.theatreColor = theatreColor; - chatData.type = CONST.CHAT_MESSAGE_TYPES.IC; - // if delay emote is active - if ( - Theatre.instance.isDelayEmote && - Theatre.instance.delayedSentState == 1 - ) { - if (Theatre.DEBUG) - console.log("setting emote now! as %s", insert.emote); - Theatre.instance.delayedSentState = 2; - Theatre.instance.setUserEmote( - game.user._id, - theatreId, - "emote", - insert.emote, - false - ); - Theatre.instance.delayedSentState = 0; - } - } else if (Theatre.instance.speakingAs == Theatre.NARRATOR) { - chatData.speaker = {}; - chatData.speaker.alias = game.i18n.localize("Theatre.UI.Chat.Narrator"); - chatData.speaker.actor = null; - chatData.speaker.scene = null; - chatData.type = CONST.CHAT_MESSAGE_TYPES.IC; - } - } - // alter message data - // append chat emote braces TODO make a setting - if (Theatre.DEBUG) console.log("speaker? ", chatMessage.data.speaker); - if ( - Theatre.instance.isQuoteAuto && - !chatMessage.data.roll && - chatMessage.data.speaker && - (chatData.speaker.actor || - chatData.speaker.token || - chatData.speaker.alias) && - !chatMessage.data.content.match(/\[\s\S]*\<\/div\>/) - ) { - chatData.content = - game.i18n.localize("Theatre.Text.OpenBracket") + - chatMessage.data.content + - game.i18n.localize("Theatre.Text.CloseBracket"); - } - - chatMessage.data.update(chatData); +Hooks.on("preCreateChatMessage", function (chatMessage) { + let chatData = { + speaker: {}, + }; + if (Theatre.DEBUG) console.log("preCreateChatMessage", chatMessage.data); + // If theatre isn't even ready, then just no + if (!Theatre.instance) return; + + // make the message OOC if needed + if (!chatMessage.data.roll && $(theatre.theatreChatCover).hasClass("theatre-control-chat-cover-ooc")) { + const user = game.users.get(chatMessage.data.user.id); + chatData.speaker.alias = user.data.name; + chatData.speaker.actor = null; + chatData.speaker.scene = null; + chatData.type = CONST.CHAT_MESSAGE_TYPES.OOC; + + chatMessage.data.update(chatData); + return; + } + + if (!chatMessage.data.roll && Theatre.instance.speakingAs && Theatre.instance.usersTyping[chatMessage.data.user.id]) { + let theatreId = Theatre.instance.usersTyping[chatMessage.data.user.id].theatreId; + let insert = Theatre.instance.getInsertById(theatreId); + let actorId = theatreId.replace("theatre-", ""); + let actor = game.actors.get(actorId) || null; + if (Theatre.DEBUG) console.log("speakingAs %s", theatreId); + + if (insert && chatMessage.data.speaker) { + let label = Theatre.instance._getLabelFromInsert(insert); + let name = label.text; + let theatreColor = Theatre.instance.getPlayerFlashColor(chatMessage.data.user.id, insert.textColor); + if (Theatre.DEBUG) console.log("name is %s", name); + chatData.speaker.alias = name; + chatData.speaker.actor = null; + chatData.speaker.scene = null; + //chatData.flags.theatreColor = theatreColor; + chatData.type = CONST.CHAT_MESSAGE_TYPES.IC; + // if delay emote is active + if (Theatre.instance.isDelayEmote && Theatre.instance.delayedSentState == 1) { + if (Theatre.DEBUG) console.log("setting emote now! as %s", insert.emote); + Theatre.instance.delayedSentState = 2; + Theatre.instance.setUserEmote(game.user._id, theatreId, "emote", insert.emote, false); + Theatre.instance.delayedSentState = 0; + } + } else if (insert) { + let label = Theatre.instance._getLabelFromInsert(insert); + let name = label.text; + let theatreColor = Theatre.instance.getPlayerFlashColor(chatData.user, insert.textColor); + chatData.speaker = {}; + chatData.speaker.alias = name; + chatData.speaker.actor = null; + chatData.speaker.scene = null; + //chatData.flags.theatreColor = theatreColor; + chatData.type = CONST.CHAT_MESSAGE_TYPES.IC; + // if delay emote is active + if (Theatre.instance.isDelayEmote && Theatre.instance.delayedSentState == 1) { + if (Theatre.DEBUG) console.log("setting emote now! as %s", insert.emote); + Theatre.instance.delayedSentState = 2; + Theatre.instance.setUserEmote(game.user._id, theatreId, "emote", insert.emote, false); + Theatre.instance.delayedSentState = 0; + } + } else if (Theatre.instance.speakingAs == Theatre.NARRATOR) { + chatData.speaker = {}; + chatData.speaker.alias = game.i18n.localize("Theatre.UI.Chat.Narrator"); + chatData.speaker.actor = null; + chatData.speaker.scene = null; + chatData.type = CONST.CHAT_MESSAGE_TYPES.IC; + } + } + // alter message data + // append chat emote braces TODO make a setting + if (Theatre.DEBUG) console.log("speaker? ", chatMessage.data.speaker); + if ( + Theatre.instance.isQuoteAuto && + !chatMessage.data.roll && + chatMessage.data.speaker && + (chatData.speaker.actor || chatData.speaker.token || chatData.speaker.alias) && + !chatMessage.data.content.match(/\[\s\S]*\<\/div\>/) + ) { + chatData.content = game.i18n.localize("Theatre.Text.OpenBracket") + chatMessage.data.content + game.i18n.localize("Theatre.Text.CloseBracket"); + } + + chatMessage.data.update(chatData); }); /** * Chat message Binding */ -Hooks.on("createChatMessage", function(chatEntity, _, userId) { - if (Theatre.DEBUG) console.log("createChatMessage"); - let theatreId = null; - - // If theatre isn't even ready, then just no - if (!Theatre.instance) return; - - if (Theatre.instance.usersTyping[userId]) { - theatreId = Theatre.instance.usersTyping[userId].theatreId; - Theatre.instance.removeUserTyping(userId); - } - - // slash commands are pass through - let chatData = chatEntity.data; - if ( - chatData.content.startsWith("<") || //Bandaid fix so that texts that start with html formatting don't utterly break it - chatData.content.startsWith("/") || - chatData.roll || - chatData.emote || - chatData.type == CONST.CHAT_MESSAGE_TYPES.OOC || - //|| Object.keys(chatData.speaker).length == 0 - chatData.content.match(/@[a-zA-Z0-9]+\[[a-zA-Z0-9]+\]/) || - chatData.content.match(/\[\s\S]*\<\/div\>/) - ) - return; - - let textBox = Theatre.instance.getTextBoxById(theatreId); - let insert = Theatre.instance.getInsertById(theatreId); - let charSpans = []; - let textContent = chatData.content; - - // replace entities - textContent = textContent.replace(/>/g, ">"); - textContent = textContent.replace(/</g, "<"); - textContent = textContent.replace(/&/g, "&"); - textContent = textContent.replace(/
/g, "\n"); - - if (textBox) { - // kill all tweens - for (let c of textBox.children) { - for (let sc of c.children) TweenMax.killTweensOf(sc); - TweenMax.killTweensOf(c); - } - for (let c of textBox.children) c.parentNode.removeChild(c); - TweenMax.killTweensOf(textBox); - textBox.style["overflow-y"] = "scroll"; - textBox.style["overflow-x"] = "hidden"; - - if (Theatre.DEBUG) console.log("all tweens", TweenMax.getAllTweens()); - textBox.textContent = ""; - - if (insert) { - // Highlight the most recent speaker's textBox - let lastSpeaking = Theatre.instance.theatreBar.getElementsByClassName( - "theatre-text-box-lastspeaking" - ); - if (lastSpeaking[0]) { - lastSpeaking[0].style.background = ""; - lastSpeaking[0].style["box-shadow"] = ""; - KHelpers.removeClass(lastSpeaking[0], "theatre-text-box-lastspeaking"); - } - KHelpers.addClass(textBox, "theatre-text-box-lastspeaking"); - Theatre.instance.applyPlayerColorToTextBox( - textBox, - userId, - insert.textColor - ); - // Pump up the speaker's render order - for (let dockInsert of Theatre.instance.portraitDocks) - dockInsert.renderOrder = dockInsert.order; - insert.renderOrder = 999999; - Theatre.instance.portraitDocks.sort((a, b) => { - return a.renderOrder - b.renderOrder; - }); - // Pop our insert a little - let tweenId = "portraitPop"; - let tween = TweenMax.to(insert.portraitContainer, 0.25, { - pixi: { scaleX: insert.mirrored ? -1.05 : 1.05, scaleY: 1.05 }, - ease: Power3.easeOut, - repeat: 1, - yoyo: true, - onComplete: function(ctx, imgId, tweenId) { - // decrement the rendering accumulator - let insert = Theatre.instance.getInsertById(imgId); - if (insert) { - this.targets()[0].scale.x = insert.mirrored ? -1 : 1; - this.targets()[0].scale.y = 1; - } - ctx._removeDockTween(imgId, this, tweenId); - // remove our own reference from the dockContainer tweens - }, - onCompleteParams: [Theatre.instance, insert.imgId, tweenId] - }); - Theatre.instance._addDockTween(insert.imgId, tween, tweenId); - // Color flash - tweenId = "portraitFlash"; - tween = TweenMax.to(insert.portrait, 0.25, { - //pixi:{tint: 0xAAEDFF}, - pixi: { - tint: Theatre.instance.getPlayerFlashColor(userId, insert.textColor) - }, - ease: Power3.easeOut, - repeat: 1, - yoyo: true, - onComplete: function(ctx, imgId, tweenId) { - // decrement the rendering accumulator - this.targets()[0].tint = 0xffffff; - ctx._removeDockTween(imgId, this, tweenId); - // remove our own reference from the dockContainer tweens - }, - onCompleteParams: [Theatre.instance, insert.imgId, tweenId] - }); - Theatre.instance._addDockTween(insert.imgId, tween, tweenId); - } - - let insertFlyinMode = "typewriter"; - let insertStandingMode = null; - let insertFontType = null; - let insertFontSize = null; - let insertFontColor = null; - if (insert) { - insertFlyinMode = insert.textFlyin; - insertStandingMode = insert.textStanding; - insertFontType = insert.textFont; - insertFontSize = Number(insert.textSize); - insertFontColor = insert.textColor; - } else if (theatreId == Theatre.NARRATOR) { - insertFlyinMode = Theatre.instance.theatreNarrator.getAttribute( - "textflyin" - ); - insertStandingMode = Theatre.instance.theatreNarrator.getAttribute( - "textstanding" - ); - insertFontType = Theatre.instance.theatreNarrator.getAttribute( - "textfont" - ); - insertFontSize = Number( - Theatre.instance.theatreNarrator.getAttribute("textsize") - ); - insertFontColor = Theatre.instance.theatreNarrator.getAttribute( - "textcolor" - ); - } - - let fontSize = Number(textBox.getAttribute("osize") || 28); - //console.log("font PRE(%s): ",insertFontSize,fontSize) - switch (insertFontSize) { - case 3: - fontSize *= 1.5; - break; - case 1: - fontSize *= 0.5; - break; - default: - break; - } - if (Theatre.DEBUG) - console.log("font size is (%s): ", insertFontSize, fontSize); - Theatre.instance._applyFontFamily( - textBox, - insertFontType || Theatre.instance.textFont - ); - //textBox.style["font-family"] = insertFontType || Theatre.instance.textFont; - textBox.style.color = insertFontColor || "white"; - textBox.style["font-size"] = `${fontSize}px`; - textBox.scrollTop = 0; - - charSpans = Theatre.splitTextBoxToChars(textContent, textBox); - - if (Theatre.DEBUG) console.log("animating text: " + textContent); - - Theatre.textFlyinAnimation(insertFlyinMode || "typewriter").call( - this, - charSpans, - 0.5, - 0.05, - Theatre.textStandingAnimation(insertStandingMode) - ); - - // auto decay? - if (insert && insert.decayTOId) window.clearTimeout(insert.decayTOId); - if (insert && Theatre.instance.settings.autoDecay) { - insert.decayTOId = window.setTimeout( - imgId => { - let insert = Theatre.instance.getInsertById(imgId); - if (insert) Theatre.instance.decayTextBoxById(imgId, true); - }, - Math.max( - Theatre.instance.settings.decayRate * charSpans.length, - Theatre.instance.settings.decayMin - ), - insert.imgId - ); - } - } +Hooks.on("createChatMessage", function (chatEntity, _, userId) { + if (Theatre.DEBUG) console.log("createChatMessage"); + let theatreId = null; + + // If theatre isn't even ready, then just no + if (!Theatre.instance) return; + + if (Theatre.instance.usersTyping[userId]) { + theatreId = Theatre.instance.usersTyping[userId].theatreId; + Theatre.instance.removeUserTyping(userId); + } + + // slash commands are pass through + let chatData = chatEntity.data; + if ( + chatData.content.startsWith("<") || //Bandaid fix so that texts that start with html formatting don't utterly break it + chatData.content.startsWith("/") || + chatData.roll || + chatData.emote || + chatData.type == CONST.CHAT_MESSAGE_TYPES.OOC || + //|| Object.keys(chatData.speaker).length == 0 + chatData.content.match(/@[a-zA-Z0-9]+\[[a-zA-Z0-9]+\]/) || + chatData.content.match(/\[\s\S]*\<\/div\>/) + ) + return; + + let textBox = Theatre.instance.getTextBoxById(theatreId); + let insert = Theatre.instance.getInsertById(theatreId); + let charSpans = []; + let textContent = chatData.content; + + // replace entities + textContent = textContent.replace(/>/g, ">"); + textContent = textContent.replace(/</g, "<"); + textContent = textContent.replace(/&/g, "&"); + textContent = textContent.replace(/
/g, "\n"); + + if (textBox) { + // kill all tweens + for (let c of textBox.children) { + for (let sc of c.children) TweenMax.killTweensOf(sc); + TweenMax.killTweensOf(c); + } + for (let c of textBox.children) c.parentNode.removeChild(c); + TweenMax.killTweensOf(textBox); + textBox.style["overflow-y"] = "scroll"; + textBox.style["overflow-x"] = "hidden"; + + if (Theatre.DEBUG) console.log("all tweens", TweenMax.getAllTweens()); + textBox.textContent = ""; + + if (insert) { + // Highlight the most recent speaker's textBox + let lastSpeaking = Theatre.instance.theatreBar.getElementsByClassName("theatre-text-box-lastspeaking"); + if (lastSpeaking[0]) { + lastSpeaking[0].style.background = ""; + lastSpeaking[0].style["box-shadow"] = ""; + KHelpers.removeClass(lastSpeaking[0], "theatre-text-box-lastspeaking"); + } + KHelpers.addClass(textBox, "theatre-text-box-lastspeaking"); + Theatre.instance.applyPlayerColorToTextBox(textBox, userId, insert.textColor); + // Pump up the speaker's render order + for (let dockInsert of Theatre.instance.portraitDocks) dockInsert.renderOrder = dockInsert.order; + insert.renderOrder = 999999; + Theatre.instance.portraitDocks.sort((a, b) => { + return a.renderOrder - b.renderOrder; + }); + // Pop our insert a little + let tweenId = "portraitPop"; + let tween = TweenMax.to(insert.portraitContainer, 0.25, { + pixi: { scaleX: insert.mirrored ? -1.05 : 1.05, scaleY: 1.05 }, + ease: Power3.easeOut, + repeat: 1, + yoyo: true, + onComplete: function (ctx, imgId, tweenId) { + // decrement the rendering accumulator + let insert = Theatre.instance.getInsertById(imgId); + if (insert) { + this.targets()[0].scale.x = insert.mirrored ? -1 : 1; + this.targets()[0].scale.y = 1; + } + ctx._removeDockTween(imgId, this, tweenId); + // remove our own reference from the dockContainer tweens + }, + onCompleteParams: [Theatre.instance, insert.imgId, tweenId], + }); + Theatre.instance._addDockTween(insert.imgId, tween, tweenId); + // Color flash + tweenId = "portraitFlash"; + tween = TweenMax.to(insert.portrait, 0.25, { + //pixi:{tint: 0xAAEDFF}, + pixi: { + tint: Theatre.instance.getPlayerFlashColor(userId, insert.textColor), + }, + ease: Power3.easeOut, + repeat: 1, + yoyo: true, + onComplete: function (ctx, imgId, tweenId) { + // decrement the rendering accumulator + this.targets()[0].tint = 0xffffff; + ctx._removeDockTween(imgId, this, tweenId); + // remove our own reference from the dockContainer tweens + }, + onCompleteParams: [Theatre.instance, insert.imgId, tweenId], + }); + Theatre.instance._addDockTween(insert.imgId, tween, tweenId); + } + + let insertFlyinMode = "typewriter"; + let insertStandingMode = null; + let insertFontType = null; + let insertFontSize = null; + let insertFontColor = null; + if (insert) { + insertFlyinMode = insert.textFlyin; + insertStandingMode = insert.textStanding; + insertFontType = insert.textFont; + insertFontSize = Number(insert.textSize); + insertFontColor = insert.textColor; + } else if (theatreId == Theatre.NARRATOR) { + insertFlyinMode = Theatre.instance.theatreNarrator.getAttribute("textflyin"); + insertStandingMode = Theatre.instance.theatreNarrator.getAttribute("textstanding"); + insertFontType = Theatre.instance.theatreNarrator.getAttribute("textfont"); + insertFontSize = Number(Theatre.instance.theatreNarrator.getAttribute("textsize")); + insertFontColor = Theatre.instance.theatreNarrator.getAttribute("textcolor"); + } + + let fontSize = Number(textBox.getAttribute("osize") || 28); + //console.log("font PRE(%s): ",insertFontSize,fontSize) + switch (insertFontSize) { + case 3: + fontSize *= 1.5; + break; + case 1: + fontSize *= 0.5; + break; + default: + break; + } + if (Theatre.DEBUG) console.log("font size is (%s): ", insertFontSize, fontSize); + Theatre.instance._applyFontFamily(textBox, insertFontType || Theatre.instance.textFont); + //textBox.style["font-family"] = insertFontType || Theatre.instance.textFont; + textBox.style.color = insertFontColor || "white"; + textBox.style["font-size"] = `${fontSize}px`; + textBox.scrollTop = 0; + + charSpans = Theatre.splitTextBoxToChars(textContent, textBox); + + if (Theatre.DEBUG) console.log("animating text: " + textContent); + + Theatre.textFlyinAnimation(insertFlyinMode || "typewriter").call(this, charSpans, 0.5, 0.05, Theatre.textStandingAnimation(insertStandingMode)); + + // auto decay? + if (insert && insert.decayTOId) window.clearTimeout(insert.decayTOId); + if (insert && Theatre.instance.settings.autoDecay) { + insert.decayTOId = window.setTimeout( + (imgId) => { + let insert = Theatre.instance.getInsertById(imgId); + if (insert) Theatre.instance.decayTextBoxById(imgId, true); + }, + Math.max(Theatre.instance.settings.decayRate * charSpans.length, Theatre.instance.settings.decayMin), + insert.imgId + ); + } + } }); -Hooks.on("renderChatLog", function(app, html, data) { - if (data.cssId === "chat-popout") return; - theatre.initialize(); - // window may not be ready? - console.log( - "%cTheatre Inserts", - "font-weight: bold; font-size: 30px; font-style: italic; color: black;" - ); - // NOTE: Closed alpha/beta is currently all rights reserved! - console.log( - "%c-- Theatre is Powered by Free Open Source GPLv3 Software --", - "font-weight: bold; font-size: 12" - ); +Hooks.on("renderChatLog", function (app, html, data) { + if (data.cssId === "chat-popout") return; + theatre.initialize(); + // window may not be ready? + console.log("%cTheatre Inserts", "font-weight: bold; font-size: 30px; font-style: italic; color: black;"); + // NOTE: Closed alpha/beta is currently all rights reserved! + console.log("%c-- Theatre is Powered by Free Open Source GPLv3 Software --", "font-weight: bold; font-size: 12"); }); /** * Add to stage button on ActorDirectory Sidebar */ Hooks.on("getActorDirectoryEntryContext", async (html, options) => { - if (!game.user.isGM && game.settings.get("theatre", "gmOnly")) return; - - const getActorData = target => { - const actor = game.actors.get(target.data("documentId")); - return actor.data; - } - - options.splice(3, 0, { - name: "Add to Stage", - condition: target => !Theatre.isActorStaged(getActorData(target)), - icon: '', - callback: target => Theatre.addToNavBar(getActorData(target)) - }, { - name: "Remove from Stage", - condition: target => Theatre.isActorStaged(getActorData(target)), - icon: '', - callback: target => Theatre.removeFromNavBar(getActorData(target)) - }); + if (!game.user.isGM && game.settings.get("theatre", "gmOnly")) return; + + const getActorData = (target) => { + const actor = game.actors.get(target.data("documentId")); + return actor.data; + }; + + options.splice( + 3, + 0, + { + name: "Add to Stage", + condition: (target) => !Theatre.isActorStaged(getActorData(target)), + icon: '', + callback: (target) => Theatre.addToNavBar(getActorData(target)), + }, + { + name: "Remove from Stage", + condition: (target) => Theatre.isActorStaged(getActorData(target)), + icon: '', + callback: (target) => Theatre.removeFromNavBar(getActorData(target)), + } + ); }); // Fixed global singleton/global object var theatre = null; Hooks.once("setup", () => { - theatre = new Theatre(); + theatre = new Theatre(); }); Hooks.once("init", () => { - // module keybinds - - game.keybindings.register("theatre", "unfocusTextArea", { - name: "Theatre.UI.Keybinds.unfocusTextArea", - hint: "", - editable: [{ - key: "Escape" - }], - onDown: () => { - if (document.activeElement === document.getElementById("chat-message")) { - event.preventDefault(); - event.stopPropagation(); - document.getElementById("chat-message").blur(); - } - }, - restricted: false - }); - - game.keybindings.register("theatre", "addOwnedToStage", { - name: "Theatre.UI.Keybinds.addOwnedToStage", - hint: "", - editable: [{ - key: "Enter", - modifiers: ['Alt'] - }], - onDown: () => { - const ownedActors = game.actors.filter(a => a.permission === 3); - const ownedTokens = ownedActors.map(a => a.getActiveTokens()); - for (const tokenArray of ownedTokens) tokenArray.forEach(t => Theatre.addToNavBar(t.actor.data)); - }, - restricted: false - }); - - game.keybindings.register("theatre", "addSelectedToStage", { - name: "Theatre.UI.Keybinds.addSelectedToStage", - hint: "", - editable: [{ - key: "Enter", - modifiers: ['Shift'] - }], - onDown: () => { - for (const tkn of canvas.tokens.controlled) Theatre.addToNavBar(tkn.actor.data); }, - restricted: false - }); - - game.keybindings.register("theatre", "narratorMode", { - name: "Theatre.UI.Keybinds.narratorMode", - hint: "", - editable: [{ - key: "KeyN", - modifiers: ['Alt'] - }], - onDown: () => { - const narratorButton = $(document).find(`div.theatre-icon-narrator`).closest(`div.theatre-control-btn`); - if (KHelpers.hasClass(narratorButton[0], "theatre-control-nav-bar-item-speakingas")) Theatre.instance.toggleNarratorBar(false); - else Theatre.instance.toggleNarratorBar(true); - - document.getElementById("chat-message").blur(); - }, - restricted: false - }); - - game.keybindings.register("theatre", "flipPortrait", { - name: "Theatre.UI.Keybinds.flipPortrait", - hint: "", - editable: [{ - key: "KeyR", - modifiers: ["Alt"] - }], - onDown: () => { - if (Theatre.instance.speakingAs) Theatre.instance.mirrorInsertById(Theatre.instance.speakingAs); - }, - restricted: false - }); - - game.keybindings.register("theatre", "nudgePortraitLeft", { - name: "Theatre.UI.Keybinds.nudgePortraitLeft", - hint: "", - editable: [{ - key: "KeyZ", - modifiers: ['Alt'] - }], - onDown: () => { - const imgId = Theatre.instance.speakingAs; - if (!imgId) return; - - const insert = Theatre.instance.portraitDocks.find(p => p.imgId === imgId); - const oleft = insert.portraitContainer.x, otop = insert.portraitContainer.y; - const tweenId = "portraitMove"; - const tween = TweenMax.to(insert.portraitContainer, 0.5, { - pixi: { x: oleft - 50, y: otop}, - ease: Power3.easeOut, - onComplete: function (ctx, imgId, tweenId) { - // decrement the rendering accumulator - ctx._removeDockTween(imgId, this, tweenId); - // remove our own reference from the dockContainer tweens - }, - onCompleteParams: [Theatre.instance, insert.imgId, tweenId] - }); - Theatre.instance._addDockTween(insert.imgId, tween, tweenId); - - // send sceneEvent - Theatre.instance._sendSceneEvent("positionupdate", { - insertid: insert.imgId, - position: { x: oleft - 50, y: otop, mirror: insert.mirrored } - }); - }, - restricted: false - }); - - game.keybindings.register("theatre", "nudgePortraitRight", { - name: "Theatre.UI.Keybinds.nudgePortraitRight", - hint: "", - editable: [{ - key: "KeyC", - modifiers: ['Alt'] - }], - onDown: () => { - const imgId = Theatre.instance.speakingAs; - if (!imgId) return; - - const insert = Theatre.instance.portraitDocks.find(p => p.imgId === imgId); - const oleft = insert.portraitContainer.x, otop = insert.portraitContainer.y; - const tweenId = "portraitMove"; - const tween = TweenMax.to(insert.portraitContainer, 0.5, { - pixi: { x: oleft + 50, y: otop }, - ease: Power3.easeOut, - onComplete: function (ctx, imgId, tweenId) { - // decrement the rendering accumulator - ctx._removeDockTween(imgId, this, tweenId); - // remove our own reference from the dockContainer tweens - }, - onCompleteParams: [Theatre.instance, insert.imgId, tweenId] - }); - Theatre.instance._addDockTween(insert.imgId, tween, tweenId); - - // send sceneEvent - Theatre.instance._sendSceneEvent("positionupdate", { - insertid: insert.imgId, - position: { x: oleft + 50, y: otop, mirror: insert.mirrored } - }); - }, - restricted: false - }); - - game.keybindings.register("theatre", "nudgePortraitUp", { - name: "Theatre.UI.Keybinds.nudgePortraitUp", - hint: "", - editable: [{ - key: "KeyS", - modifiers: ['Alt'] - }], - onDown: () => { - const imgId = Theatre.instance.speakingAs; - if (!imgId) return; - - const insert = Theatre.instance.portraitDocks.find(p => p.imgId === imgId); - const oleft = insert.portraitContainer.x, otop = insert.portraitContainer.y; - const tweenId = "portraitMove"; - const tween = TweenMax.to(insert.portraitContainer, 0.5, { - pixi: { x: oleft, y: otop - 50}, - ease: Power3.easeOut, - onComplete: function (ctx, imgId, tweenId) { - // decrement the rendering accumulator - ctx._removeDockTween(imgId, this, tweenId); - // remove our own reference from the dockContainer tweens - }, - onCompleteParams: [Theatre.instance, insert.imgId, tweenId] - }); - Theatre.instance._addDockTween(insert.imgId, tween, tweenId); - - // send sceneEvent - Theatre.instance._sendSceneEvent("positionupdate", { - insertid: insert.imgId, - position: { x: oleft, y: otop - 50, mirror: insert.mirrored } - }); - }, - restricted: false - }); - - game.keybindings.register("theatre", "nudgePortraitDown", { - name: "Theatre.UI.Keybinds.nudgePortraitDown", - hint: "", - editable: [{ - key: "KeyX", - modifiers: ['Alt'] - }], - onDown: () => { - const imgId = Theatre.instance.speakingAs; - if (!imgId) return; - - const insert = Theatre.instance.portraitDocks.find(p => p.imgId === imgId); - const oleft = insert.portraitContainer.x, otop = insert.portraitContainer.y; - const tweenId = "portraitMove"; - const tween = TweenMax.to(insert.portraitContainer, 0.5, { - pixi: { x: oleft, y: otop + 50}, - ease: Power3.easeOut, - onComplete: function (ctx, imgId, tweenId) { - // decrement the rendering accumulator - ctx._removeDockTween(imgId, this, tweenId); - // remove our own reference from the dockContainer tweens - }, - onCompleteParams: [Theatre.instance, insert.imgId, tweenId] - }); - Theatre.instance._addDockTween(insert.imgId, tween, tweenId); - - // send sceneEvent - Theatre.instance._sendSceneEvent("positionupdate", { - insertid: insert.imgId, - position: { x: oleft, y: otop + 50, mirror: insert.mirrored } - }); - }, - restricted: false - }); - - - for (let i = 1; i < 11; i++) { - game.keybindings.register("theatre", `activateStaged${i}`, { - name: `Theatre.UI.Keybinds.activateStaged${i}`, - hint: "", - editable: [{ - key: `Digit${ i === 10 ? 0 : i}`, - modifiers: ["Control"] - }], - onDown: () => { - const ids = Object.keys(Theatre.instance.stage); - const id = ids[i - 1]; - if (id) Theatre.instance.activateInsertById(id); - - document.getElementById("chat-message").blur(); - }, - restricted: false - }); - - game.keybindings.register("theatre", `removeStaged${i}`, { - name: `Theatre.UI.Keybinds.removeStaged${i}`, - hint: "", - editable: [{ - key: `Digit${ i === 10 ? 0 : i}`, - modifiers: ["Control", "Alt"] - }], - onDown: () => { - const ids = Object.keys(Theatre.instance.stage); - const id = ids[i - 1]; - if (id) Theatre.instance.removeInsertById(id); - }, - restricted: false - }); - } - + // module keybinds + + game.keybindings.register("theatre", "unfocusTextArea", { + name: "Theatre.UI.Keybinds.unfocusTextArea", + hint: "", + editable: [ + { + key: "Escape", + }, + ], + onDown: () => { + if (document.activeElement === document.getElementById("chat-message")) { + event.preventDefault(); + event.stopPropagation(); + document.getElementById("chat-message").blur(); + } + }, + restricted: false, + }); + + game.keybindings.register("theatre", "addOwnedToStage", { + name: "Theatre.UI.Keybinds.addOwnedToStage", + hint: "", + editable: [ + { + key: "Enter", + modifiers: ["Alt"], + }, + ], + onDown: () => { + const ownedActors = game.actors.filter((a) => a.permission === 3); + const ownedTokens = ownedActors.map((a) => a.getActiveTokens()); + for (const tokenArray of ownedTokens) tokenArray.forEach((t) => Theatre.addToNavBar(t.actor.data)); + }, + restricted: false, + }); + + game.keybindings.register("theatre", "addSelectedToStage", { + name: "Theatre.UI.Keybinds.addSelectedToStage", + hint: "", + editable: [ + { + key: "Enter", + modifiers: ["Shift"], + }, + ], + onDown: () => { + for (const tkn of canvas.tokens.controlled) Theatre.addToNavBar(tkn.actor.data); + }, + restricted: false, + }); + + game.keybindings.register("theatre", "narratorMode", { + name: "Theatre.UI.Keybinds.narratorMode", + hint: "", + editable: [ + { + key: "KeyN", + modifiers: ["Alt"], + }, + ], + onDown: () => { + const narratorButton = $(document).find(`div.theatre-icon-narrator`).closest(`div.theatre-control-btn`); + if (KHelpers.hasClass(narratorButton[0], "theatre-control-nav-bar-item-speakingas")) Theatre.instance.toggleNarratorBar(false); + else Theatre.instance.toggleNarratorBar(true); + + document.getElementById("chat-message").blur(); + }, + restricted: false, + }); + + game.keybindings.register("theatre", "flipPortrait", { + name: "Theatre.UI.Keybinds.flipPortrait", + hint: "", + editable: [ + { + key: "KeyR", + modifiers: ["Alt"], + }, + ], + onDown: () => { + if (Theatre.instance.speakingAs) Theatre.instance.mirrorInsertById(Theatre.instance.speakingAs); + }, + restricted: false, + }); + + game.keybindings.register("theatre", "nudgePortraitLeft", { + name: "Theatre.UI.Keybinds.nudgePortraitLeft", + hint: "", + editable: [ + { + key: "KeyZ", + modifiers: ["Alt"], + }, + ], + onDown: () => { + const imgId = Theatre.instance.speakingAs; + if (!imgId) return; + + const insert = Theatre.instance.portraitDocks.find((p) => p.imgId === imgId); + const oleft = insert.portraitContainer.x, + otop = insert.portraitContainer.y; + const tweenId = "portraitMove"; + const tween = TweenMax.to(insert.portraitContainer, 0.5, { + pixi: { x: oleft - 50, y: otop }, + ease: Power3.easeOut, + onComplete: function (ctx, imgId, tweenId) { + // decrement the rendering accumulator + ctx._removeDockTween(imgId, this, tweenId); + // remove our own reference from the dockContainer tweens + }, + onCompleteParams: [Theatre.instance, insert.imgId, tweenId], + }); + Theatre.instance._addDockTween(insert.imgId, tween, tweenId); + + // send sceneEvent + Theatre.instance._sendSceneEvent("positionupdate", { + insertid: insert.imgId, + position: { x: oleft - 50, y: otop, mirror: insert.mirrored }, + }); + }, + restricted: false, + }); + + game.keybindings.register("theatre", "nudgePortraitRight", { + name: "Theatre.UI.Keybinds.nudgePortraitRight", + hint: "", + editable: [ + { + key: "KeyC", + modifiers: ["Alt"], + }, + ], + onDown: () => { + const imgId = Theatre.instance.speakingAs; + if (!imgId) return; + + const insert = Theatre.instance.portraitDocks.find((p) => p.imgId === imgId); + const oleft = insert.portraitContainer.x, + otop = insert.portraitContainer.y; + const tweenId = "portraitMove"; + const tween = TweenMax.to(insert.portraitContainer, 0.5, { + pixi: { x: oleft + 50, y: otop }, + ease: Power3.easeOut, + onComplete: function (ctx, imgId, tweenId) { + // decrement the rendering accumulator + ctx._removeDockTween(imgId, this, tweenId); + // remove our own reference from the dockContainer tweens + }, + onCompleteParams: [Theatre.instance, insert.imgId, tweenId], + }); + Theatre.instance._addDockTween(insert.imgId, tween, tweenId); + + // send sceneEvent + Theatre.instance._sendSceneEvent("positionupdate", { + insertid: insert.imgId, + position: { x: oleft + 50, y: otop, mirror: insert.mirrored }, + }); + }, + restricted: false, + }); + + game.keybindings.register("theatre", "nudgePortraitUp", { + name: "Theatre.UI.Keybinds.nudgePortraitUp", + hint: "", + editable: [ + { + key: "KeyS", + modifiers: ["Alt"], + }, + ], + onDown: () => { + const imgId = Theatre.instance.speakingAs; + if (!imgId) return; + + const insert = Theatre.instance.portraitDocks.find((p) => p.imgId === imgId); + const oleft = insert.portraitContainer.x, + otop = insert.portraitContainer.y; + const tweenId = "portraitMove"; + const tween = TweenMax.to(insert.portraitContainer, 0.5, { + pixi: { x: oleft, y: otop - 50 }, + ease: Power3.easeOut, + onComplete: function (ctx, imgId, tweenId) { + // decrement the rendering accumulator + ctx._removeDockTween(imgId, this, tweenId); + // remove our own reference from the dockContainer tweens + }, + onCompleteParams: [Theatre.instance, insert.imgId, tweenId], + }); + Theatre.instance._addDockTween(insert.imgId, tween, tweenId); + + // send sceneEvent + Theatre.instance._sendSceneEvent("positionupdate", { + insertid: insert.imgId, + position: { x: oleft, y: otop - 50, mirror: insert.mirrored }, + }); + }, + restricted: false, + }); + + game.keybindings.register("theatre", "nudgePortraitDown", { + name: "Theatre.UI.Keybinds.nudgePortraitDown", + hint: "", + editable: [ + { + key: "KeyX", + modifiers: ["Alt"], + }, + ], + onDown: () => { + const imgId = Theatre.instance.speakingAs; + if (!imgId) return; + + const insert = Theatre.instance.portraitDocks.find((p) => p.imgId === imgId); + const oleft = insert.portraitContainer.x, + otop = insert.portraitContainer.y; + const tweenId = "portraitMove"; + const tween = TweenMax.to(insert.portraitContainer, 0.5, { + pixi: { x: oleft, y: otop + 50 }, + ease: Power3.easeOut, + onComplete: function (ctx, imgId, tweenId) { + // decrement the rendering accumulator + ctx._removeDockTween(imgId, this, tweenId); + // remove our own reference from the dockContainer tweens + }, + onCompleteParams: [Theatre.instance, insert.imgId, tweenId], + }); + Theatre.instance._addDockTween(insert.imgId, tween, tweenId); + + // send sceneEvent + Theatre.instance._sendSceneEvent("positionupdate", { + insertid: insert.imgId, + position: { x: oleft, y: otop + 50, mirror: insert.mirrored }, + }); + }, + restricted: false, + }); + + for (let i = 1; i < 11; i++) { + game.keybindings.register("theatre", `activateStaged${i}`, { + name: `Theatre.UI.Keybinds.activateStaged${i}`, + hint: "", + editable: [ + { + key: `Digit${i === 10 ? 0 : i}`, + modifiers: ["Control"], + }, + ], + onDown: () => { + const ids = Object.keys(Theatre.instance.stage); + const id = ids[i - 1]; + if (id) Theatre.instance.activateInsertById(id); + + document.getElementById("chat-message").blur(); + }, + restricted: false, + }); + + game.keybindings.register("theatre", `removeStaged${i}`, { + name: `Theatre.UI.Keybinds.removeStaged${i}`, + hint: "", + editable: [ + { + key: `Digit${i === 10 ? 0 : i}`, + modifiers: ["Control", "Alt"], + }, + ], + onDown: () => { + const ids = Object.keys(Theatre.instance.stage); + const id = ids[i - 1]; + if (id) Theatre.instance.removeInsertById(id); + }, + restricted: false, + }); + } }); /** * Hide player list (and macro hotbar) when stage is active (and not suppressed) */ -Hooks.on("theatreDockActive", insertCount => { - if (!insertCount) return; +Hooks.on("theatreDockActive", (insertCount) => { + if (!insertCount) return; - // The "MyTab" module inserts another element with id "pause". Use querySelectorAll to make sure we catch both - document.querySelectorAll("#pause").forEach(ele => KHelpers.addClass(ele, "theatre-centered")); + // The "MyTab" module inserts another element with id "pause". Use querySelectorAll to make sure we catch both + document.querySelectorAll("#pause").forEach((ele) => KHelpers.addClass(ele, "theatre-centered")); - if (!game.settings.get(Theatre.SETTINGS, "autoHideBottom")) return; + if (!game.settings.get(Theatre.SETTINGS, "autoHideBottom")) return; - if (!theatre.isSuppressed) { - $('#players').addClass("theatre-invisible"); - $('#hotbar').addClass("theatre-invisible"); - } + if (!theatre.isSuppressed) { + $("#players").addClass("theatre-invisible"); + $("#hotbar").addClass("theatre-invisible"); + } }); /** * If Argon is active, wrap CombatHudCanvasElement#toggleMacroPlayers to prevent playesr list and macro hotbar from being shown */ - Hooks.once("ready", () => { - if (!game.settings.get(Theatre.SETTINGS, "autoHideBottom")) return; - if (!game.modules.get("enhancedcombathud")?.active) return; - - libWrapper.register(Theatre.SETTINGS, "CombatHudCanvasElement.prototype.toggleMacroPlayers", (wrapped, togg) => { - if (togg && theatre?.dockActive) return; - return wrapped(togg); - }, "MIXED"); +Hooks.once("ready", () => { + if (!game.settings.get(Theatre.SETTINGS, "autoHideBottom")) return; + if (!game.modules.get("enhancedcombathud")?.active) return; + + libWrapper.register( + Theatre.SETTINGS, + "CombatHudCanvasElement.prototype.toggleMacroPlayers", + (wrapped, togg) => { + if (togg && theatre?.dockActive) return; + return wrapped(togg); + }, + "MIXED" + ); }); /** * Hide/show macro hotbar when stage is suppressed */ -Hooks.on("theatreSuppression", suppressed => { - if (!game.settings.get(Theatre.SETTINGS, "autoHideBottom")) return; - if (!game.settings.get(Theatre.SETTINGS, "suppressMacroHotbar")) return; - if (!theatre.dockActive) return; - - if (suppressed) { - $("#players").removeClass("theatre-invisible"); - $("#hotbar").removeClass("theatre-invisible"); - } - else { - $("#players").addClass("theatre-invisible"); - $("#hotbar").addClass("theatre-invisible"); - } +Hooks.on("theatreSuppression", (suppressed) => { + if (!game.settings.get(Theatre.SETTINGS, "autoHideBottom")) return; + if (!game.settings.get(Theatre.SETTINGS, "suppressMacroHotbar")) return; + if (!theatre.dockActive) return; + + if (suppressed) { + $("#players").removeClass("theatre-invisible"); + $("#hotbar").removeClass("theatre-invisible"); + } else { + $("#players").addClass("theatre-invisible"); + $("#hotbar").addClass("theatre-invisible"); + } }); Hooks.on("renderPause", () => { - if (!theatre?.dockActive) return; - // The "MyTab" module inserts another element with id "pause". Use querySelectorAll to make sure we catch both - document.querySelectorAll("#pause").forEach(ele => KHelpers.addClass(ele, "theatre-centered")); + if (!theatre?.dockActive) return; + // The "MyTab" module inserts another element with id "pause". Use querySelectorAll to make sure we catch both + document.querySelectorAll("#pause").forEach((ele) => KHelpers.addClass(ele, "theatre-centered")); }); /** * If an actor changes, update the stage accordingly */ Hooks.on("updateActor", (actor, data) => { - const insert = Theatre.instance.getInsertById(`theatre-${actor.id}`); - if (!insert) return; + const insert = Theatre.instance.getInsertById(`theatre-${actor.id}`); + if (!insert) return; - insert.label.text = Theatre.getActorDisplayName(actor.id); - Theatre.instance._renderTheatre(performance.now()); + insert.label.text = Theatre.getActorDisplayName(actor.id); + Theatre.instance._renderTheatre(performance.now()); }); -Hooks.on("getSceneControlButtons", controls => { - // Use "theatre", since Theatre.SETTINGS may not be available yet - if (!game.user.isGM && game.settings.get("theatre", "gmOnly")) { - const suppressTheatreTool = { - name: "suppressTheatre", - title: "Theatre.UI.Title.SuppressTheatre", - icon: "fas fa-theater-masks", - toggle: true, - active: false, - onClick: toggle => Theatre.instance.updateSuppression(toggle), // TODO Suppress theatre - visible: true, - }; - const tokenControls = controls.find(group => group.name === "token").tools; - tokenControls.push(suppressTheatreTool); - } -}) +Hooks.on("getSceneControlButtons", (controls) => { + // Use "theatre", since Theatre.SETTINGS may not be available yet + if (!game.user.isGM && game.settings.get("theatre", "gmOnly")) { + const suppressTheatreTool = { + name: "suppressTheatre", + title: "Theatre.UI.Title.SuppressTheatre", + icon: "fas fa-theater-masks", + toggle: true, + active: false, + onClick: (toggle) => Theatre.instance.updateSuppression(toggle), // TODO Suppress theatre + visible: true, + }; + const tokenControls = controls.find((group) => group.name === "token").tools; + tokenControls.push(suppressTheatreTool); + } +}); From 844755b5067eebc54ace2634702f77e4bebd0b71 Mon Sep 17 00:00:00 2001 From: Matheus Clemente Date: Thu, 9 Feb 2023 16:54:06 -0300 Subject: [PATCH 2/4] Prettier code formatting 2 --- module.json | 156 ++++++++++++++++++++++++++-------------------------- 1 file changed, 77 insertions(+), 79 deletions(-) diff --git a/module.json b/module.json index 3f9150d..80b217a 100644 --- a/module.json +++ b/module.json @@ -1,81 +1,79 @@ { - "name": "theatre", - "title": "Theatre Inserts", - "description": "Theater Inserts with a visual novel style made for heavy roleplay scenes", - "version": "1.16.2", - "author": "Ken L, Noah Zorbaugh, U~man, KaKaRoTo, elizeuangelo", - "socket": true, - "languages": [ - { - "lang": "en", - "name": "English", - "path": "app/lang/en.json" - }, - { - "lang": "ja", - "name": "日本語 (Japanese)", - "path": "app/lang/ja.json" - }, - { - "lang": "ko", - "name": "한국어 (Korean)", - "path": "app/lang/ko.json" - }, - { - "lang": "pt-BR", - "name": "Português (Portuguese [Brasil])", - "path": "app/lang/pt-BR.json" - }, - { - "lang": "fr", - "name": "Français (French)", - "path": "app/lang/fr.json" - }, - { - "lang": "th", - "name": "ภาษาไทย (Thai)", - "path": "app/lang/th.json" - }, - { - "lang": "zh-tw", - "name": "正體中文", - "path": "app/lang/zh-tw.json" - }, - { - "lang": "es", - "name": "Español", - "path": "app/lang/es.json" - }, - { - "lang": "de", - "name": "Deutsch (German)", - "path": "app/lang/de.json" - } - ], - "scripts": [ - "greensock/dist/gsap.min.js", - "greensock/dist/PixiPlugin.min.js", - "greensock/dist/ScrollToPlugin.min.js", - "greensock/dist/SplitText.min.js", - "app/js/TheatreActorConfig.js", - "app/js/TheatreActor.js", - "app/js/Theatre.js", - "app/js/theatre_main.js" - ], - "styles": [ - "app/css/theatre.css" - ], - "packs": [ - { - "name": "theatre-inserts-macros", - "label": "Theatre Inserts Macros", - "path": "app/packs/theatre-inserts-macros.db", - "entity": "Macro" - } - ], - "url": "https://github.com/League-of-Foundry-Developers/fvtt-module-theatre", - "download": "https://github.com/League-of-Foundry-Developers/fvtt-module-theatre/releases/download/v1.16.2/theatre.zip", - "manifest": "https://github.com/League-of-Foundry-Developers/fvtt-module-theatre/releases/download/latest/module.json", - "minimumCoreVersion": "10", - "compatibleCoreVersion": "10" + "name": "theatre", + "title": "Theatre Inserts", + "description": "Theater Inserts with a visual novel style made for heavy roleplay scenes", + "version": "1.16.2", + "author": "Ken L, Noah Zorbaugh, U~man, KaKaRoTo, elizeuangelo", + "socket": true, + "languages": [ + { + "lang": "en", + "name": "English", + "path": "app/lang/en.json" + }, + { + "lang": "ja", + "name": "日本語 (Japanese)", + "path": "app/lang/ja.json" + }, + { + "lang": "ko", + "name": "한국어 (Korean)", + "path": "app/lang/ko.json" + }, + { + "lang": "pt-BR", + "name": "Português (Portuguese [Brasil])", + "path": "app/lang/pt-BR.json" + }, + { + "lang": "fr", + "name": "Français (French)", + "path": "app/lang/fr.json" + }, + { + "lang": "th", + "name": "ภาษาไทย (Thai)", + "path": "app/lang/th.json" + }, + { + "lang": "zh-tw", + "name": "正體中文", + "path": "app/lang/zh-tw.json" + }, + { + "lang": "es", + "name": "Español", + "path": "app/lang/es.json" + }, + { + "lang": "de", + "name": "Deutsch (German)", + "path": "app/lang/de.json" + } + ], + "scripts": [ + "greensock/dist/gsap.min.js", + "greensock/dist/PixiPlugin.min.js", + "greensock/dist/ScrollToPlugin.min.js", + "greensock/dist/SplitText.min.js", + "app/js/TheatreActorConfig.js", + "app/js/TheatreActor.js", + "app/js/Theatre.js", + "app/js/theatre_main.js" + ], + "styles": ["app/css/theatre.css"], + "packs": [ + { + "name": "theatre-inserts-macros", + "label": "Theatre Inserts Macros", + "path": "app/packs/theatre-inserts-macros.db", + "entity": "Macro" + } + ], + "url": "https://github.com/League-of-Foundry-Developers/fvtt-module-theatre", + "download": "https://github.com/League-of-Foundry-Developers/fvtt-module-theatre/releases/download/v1.16.2/theatre.zip", + "manifest": "https://github.com/League-of-Foundry-Developers/fvtt-module-theatre/releases/download/latest/module.json", + "minimumCoreVersion": "10", + "compatibleCoreVersion": "10" } From 5f7ee6c29b178b5e09d12314dac8b0de365f436e Mon Sep 17 00:00:00 2001 From: Matheus Clemente Date: Thu, 9 Feb 2023 16:59:33 -0300 Subject: [PATCH 3/4] Update module.json --- module.json | 33 ++++++++++++++++++++++++++------- 1 file changed, 26 insertions(+), 7 deletions(-) diff --git a/module.json b/module.json index 80b217a..a272e61 100644 --- a/module.json +++ b/module.json @@ -1,9 +1,25 @@ { - "name": "theatre", + "id": "theatre", "title": "Theatre Inserts", "description": "Theater Inserts with a visual novel style made for heavy roleplay scenes", - "version": "1.16.2", - "author": "Ken L, Noah Zorbaugh, U~man, KaKaRoTo, elizeuangelo", + "version": "2.3.1", + "authors": [ + { + "name": "Ken L" + }, + { + "name": "Noah Zorbaugh" + }, + { + "name": "U~man" + }, + { + "name": "KaKaRoTo" + }, + { + "name": "elizeuangelo" + } + ], "socket": true, "languages": [ { @@ -68,12 +84,15 @@ "name": "theatre-inserts-macros", "label": "Theatre Inserts Macros", "path": "app/packs/theatre-inserts-macros.db", - "entity": "Macro" + "type": "Macro", + "private": false } ], "url": "https://github.com/League-of-Foundry-Developers/fvtt-module-theatre", - "download": "https://github.com/League-of-Foundry-Developers/fvtt-module-theatre/releases/download/v1.16.2/theatre.zip", + "download": "https://github.com/League-of-Foundry-Developers/fvtt-module-theatre/releases/download/latest/theatre.zip", "manifest": "https://github.com/League-of-Foundry-Developers/fvtt-module-theatre/releases/download/latest/module.json", - "minimumCoreVersion": "10", - "compatibleCoreVersion": "10" + "compatibility": { + "minimum": "10", + "verified": "10" + } } From f1003b1852720be756dc8a89b4b354cd2cfc1d1e Mon Sep 17 00:00:00 2001 From: Matheus Clemente Date: Thu, 9 Feb 2023 19:46:06 -0300 Subject: [PATCH 4/4] Lots of improvements Removed deprecated warnings. Fixed update() calls that should be updateSource(). Fix #108 Fix #112 #113 --- app/js/Theatre.js | 624 +++++++++++++++++++++------- app/js/TheatreActor.js | 8 +- app/js/TheatreActorConfig.js | 60 +-- app/js/theatre_main.js | 95 +++-- app/lang/en.json | 420 ++++++++++--------- app/packs/theatre-inserts-macros.db | 4 +- 6 files changed, 787 insertions(+), 424 deletions(-) diff --git a/app/js/Theatre.js b/app/js/Theatre.js index 23d6dfb..0f70262 100644 --- a/app/js/Theatre.js +++ b/app/js/Theatre.js @@ -96,6 +96,20 @@ class Theatre { return Theatre.instance; } + functions = { + addToNavBar: (actor) => Theatre.addToNavBar(actor), + removeFromNavBar: (actor) => Theatre.removeFromNavBar(actor), + activateStagedByID: (i) => { + const ids = Object.keys(Theatre.instance.stage); + Theatre.instance.activateInsertById(ids[i]); + document.getElementById("chat-message").blur(); + }, + removeFromStagedByID: (i) => { + const ids = Object.keys(Theatre.instance.stage); + Theatre.instance.removeInsertById(ids[i]); + }, + }; + initialize() { // inject HTML this._injectHTML(); @@ -487,10 +501,43 @@ class Theatre { default: false, }); + game.settings.register(Theatre.SETTINGS, "ignoreMessagesToChat", { + name: "Theatre.UI.Settings.ignoreMessagesToChat", + hint: "Theatre.UI.Settings.ignoreMessagesToChatHint", + scope: "world", + config: true, + type: Boolean, + default: false, + onChange: (value) => { + this.settings.ignoreMessagesToChat = value; + }, + }); + + game.settings.register(Theatre.SETTINGS, "quoteType", { + name: "Theatre.UI.Settings.quoteType", + hint: game.i18n.format("Theatre.UI.Settings.quoteTypeHint", { setting: game.i18n.localize("Theatre.UI.Title.QuoteToggle") }), + scope: "world", + config: true, + type: Number, + default: 1, + choices: { + 0: game.i18n.localize("Theatre.UI.Settings.quoteTypeChoices.0"), + 1: game.i18n.localize("Theatre.UI.Settings.quoteTypeChoices.1"), + 2: game.i18n.localize("Theatre.UI.Settings.quoteTypeChoices.2"), + 3: game.i18n.localize("Theatre.UI.Settings.quoteTypeChoices.3"), + 4: game.i18n.localize("Theatre.UI.Settings.quoteTypeChoices.4"), + }, + onChange: (value) => { + this.settings.quoteType = value; + }, + }); + // Load in default settings (theatreStyle is loaded on HTML Injection) this.settings.decayMin = (game.settings.get(Theatre.SETTINGS, "textDecayMin") || 30) * 1000; this.settings.decayRate = (game.settings.get(Theatre.SETTINGS, "textDecayRate") || 1) * 1000; this.settings.motdNewInfo = game.settings.get(Theatre.SETTINGS, "motdNewInfo") || 1; + this.settings.ignoreMessagesToChat = game.settings.get(Theatre.SETTINGS, "ignoreMessagesToChat"); + this.settings.quoteType = game.settings.get(Theatre.SETTINGS, "quoteType"); } /** @@ -879,7 +926,7 @@ class Theatre { for (let insert of this.portraitDocks) this.removeInsertById(insert.imgId, true); if (type == "gm") ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.ResyncGM")); - else ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.ResyncPlayer") + game.users.get(senderId).data.name); + else ui.notifications.info(game.i18n.localize("Theatre.UI.Notification.ResyncPlayer") + game.users.get(senderId).name); let theatreId, insert, port, actorId, actor, params; let toInject = []; @@ -974,7 +1021,7 @@ class Theatre { // apply mirror state /* if (Boolean(dat.position.mirror) != insert.mirrored) - this._mirrorInsert(port,true); + this._mirrorInsert(port,true); */ if (Theatre.DEBUG) console.log("Mirror ? %s : %s", dat.position.mirror, insert.mirrored); if (Boolean(dat.position.mirror) != insert.mirrored) { @@ -1697,7 +1744,6 @@ class Theatre { console.log("ERROR, ACTOR %s DOES NOT EXIST!", actorId); return null; } - actor = actor.data; //console.log("getting params from actor: ",actor); let theatreId = `theatre-${actor._id}`; @@ -1746,7 +1792,7 @@ class Theatre { if (Theatre.DEBUG) console.log("isDefaultDisabled ", actor); - if (actor.data.flags.theatre && actor.data.flags.theatre.disabledefault) return true; + if (actor.flags.theatre && actor.flags.theatre.disabledefault) return true; return false; } @@ -1769,8 +1815,7 @@ class Theatre { console.log("ERROR, ACTOR %s DOES NOT EXIST!", actorId); return false; } - actor = actor.data; - if ((actor.permission[userId] && actor.permission[userId] >= 3) || (actor.permission["default"] && actor.permission["default"] >= 3)) return true; + if ((actor.ownership[userId] && actor.ownership[userId] >= 3) || (actor.ownership["default"] && actor.ownership["default"] >= 3)) return true; return false; } @@ -1791,13 +1836,12 @@ class Theatre { console.log("ERROR, ACTOR %s DOES NOT EXIST!", actorId); return; } - actor = actor.data; - for (let perm in actor.permission) { + for (let perm in actor.ownership) { if (perm != "default") { user = game.users.get(perm); if (!user.isGM) return true; } else { - if (actor.permission[perm] >= 1) return true; + if (actor.ownership[perm] >= 1) return true; } } return false; @@ -1952,33 +1996,33 @@ class Theatre { // face detect /* faceapi.detectSingleFace(app.view,new faceapi.TinyFaceDetectorOptions()).then((detection)=>{ - console.log("face detected: ", detection); + console.log("face detected: ", detection); if (detection) { - let box = detection.box; - console.log("successful preview face detection: ", box); - let graphics = new PIXI.Graphics(); - graphics.lineStyle (2,0xFFFFFF,1); + let box = detection.box; + console.log("successful preview face detection: ", box); + let graphics = new PIXI.Graphics(); + graphics.lineStyle (2,0xFFFFFF,1); if (maxSide == portWidth) { graphics.moveTo(box.x/(ratio*2)+70,box.y/(ratio*2)); graphics.lineTo(box.x/(ratio*2) + box.width/(ratio*2)+70,box.y/(ratio*2)); - graphics.lineTo(box.x/(ratio*2) + box.width/(ratio*2)+70,box.y/(ratio*2)+box.height/(ratio*2)); - graphics.lineTo(box.x/(ratio*2)+70,box.y/(ratio*2)+box.height/(ratio*2)); - graphics.lineTo(box.x/(ratio*2)+70,box.y/(ratio*2)); + graphics.lineTo(box.x/(ratio*2) + box.width/(ratio*2)+70,box.y/(ratio*2)+box.height/(ratio*2)); + graphics.lineTo(box.x/(ratio*2)+70,box.y/(ratio*2)+box.height/(ratio*2)); + graphics.lineTo(box.x/(ratio*2)+70,box.y/(ratio*2)); } else { graphics.moveTo(box.x/(ratio*2),box.y/(ratio*2)+70); graphics.lineTo(box.x/(ratio*2) + box.width/(ratio*2),box.y/(ratio*2)+70); - graphics.lineTo(box.x/(ratio*2) + box.width/(ratio*2),box.y/(ratio*2)+box.height/(ratio*2)+70); - graphics.lineTo(box.x/(ratio*2),box.y/(ratio*2)+box.height/(ratio*2)+70); - graphics.lineTo(box.x/(ratio*2),box.y/(ratio*2)+70); + graphics.lineTo(box.x/(ratio*2) + box.width/(ratio*2),box.y/(ratio*2)+box.height/(ratio*2)+70); + graphics.lineTo(box.x/(ratio*2),box.y/(ratio*2)+box.height/(ratio*2)+70); + graphics.lineTo(box.x/(ratio*2),box.y/(ratio*2)+70); } - app.stage.addChild(graphics); - app.render(); + app.stage.addChild(graphics); + app.render(); } else { - console.log("FAILED TO FIND PREVIEW FACE"); + console.log("FAILED TO FIND PREVIEW FACE"); } - this.theatreToolTip.style.opacity = 1; - }); + this.theatreToolTip.style.opacity = 1; + }); */ } @@ -2257,7 +2301,10 @@ class Theatre { let imgSrcs = []; - imgSrcs.push({ imgpath: "modules/theatre/app/graphics/typing.png", resname: "modules/theatre/app/graphics/typing.png" }); + imgSrcs.push({ + imgpath: "modules/theatre/app/graphics/typing.png", + resname: "modules/theatre/app/graphics/typing.png", + }); imgSrcs.push({ imgpath: imgPath, resname: imgPath }); if (Theatre.DEBUG) console.log("Adding %s with src %s", portName, imgPath); // get actor, load all emote images @@ -2381,7 +2428,7 @@ class Theatre { portraitContainer.scale.x = -1; /* if (reorder) - portraitContainer.x = portWidth; + portraitContainer.x = portWidth; */ } // setup label if not setup @@ -2724,7 +2771,7 @@ class Theatre { let loader = PIXI.Loader.shared; /* if (loader.resources[resName]) - loader.resources[resName] = null; + loader.resources[resName] = null; */ // if we have no resName then just return the cb @@ -2795,7 +2842,7 @@ class Theatre { let loader = PIXI.Loader.shared; /* if (loader.resources[resName]) - loader.resources[resName] = null; + loader.resources[resName] = null; */ // if we have an emtpy imgSrc array, just return the cb @@ -3085,8 +3132,8 @@ class Theatre { let actor = game.actors.get(actorId); if (!actor) return; - let baseInsert = actor.data.img ? actor.data.img : "icons/mystery-man.png"; - if (actor.data.flags.theatre) baseInsert = actor.data.flags.theatre.baseinsert ? actor.data.flags.theatre.baseinsert : baseInsert; + let baseInsert = actor.img ? actor.img : "icons/mystery-man.png"; + if (actor.flags.theatre) baseInsert = actor.flags.theatre.baseinsert ? actor.flags.theatre.baseinsert : baseInsert; let emotes = Theatre.getActorEmotes(actorId); // emote already active @@ -3670,7 +3717,7 @@ class Theatre { TweenMax.killTweensOf(toRemoveTextBox); /* for (let c of toRemoveTextBox.children) - c.parentNode.removeChild(c); + c.parentNode.removeChild(c); */ // fade away text box toRemoveTextBox.style.opacity = 0; @@ -4278,12 +4325,12 @@ class Theatre { /* if (this.reorderTOId) - window.clearTimeout(this.reorderTOId); + window.clearTimeout(this.reorderTOId); this.reorderTOId = window.setTimeout(()=>{ - Theatre.reorderInserts(); - this.reorderTOId = null; - },500); + Theatre.reorderInserts(); + this.reorderTOId = null; + },500); */ Theatre.reorderInserts(); @@ -4553,7 +4600,7 @@ class Theatre { yoyo: yoyo, yoyoEase: yoyoEase, /*onRepeat: function() { - console.log("ANIMATION tween is repeating!",this); + console.log("ANIMATION tween is repeating!",this); }, */ onComplete: function (ctx, imgId, tweenId) { if (Theatre.DEBUG) console.log("ANIMATION tween complete!"); @@ -4573,8 +4620,8 @@ class Theatre { * intitial emotion set when displaying an insert * which was previously staged, or not active * - * first : actor.data.flags.theatre..settings. - * second : actor.data.flags.theatre.settings. + * first : actor.flags.theatre..settings. + * second : actor.flags.theatre.settings. * third : Theatre.instance.userEmotes[]. * * @params params (Object) : The set of emotion properties. @@ -4634,7 +4681,7 @@ class Theatre { let navItem = this.getNavItemById(id); if (!navItem) { let actor = game.actors.get(actorId); - Theatre.addToNavBar(actor.data); + Theatre.addToNavBar(actor); navItem = this.getNavItemById(id); } if (!navItem) return; @@ -4673,7 +4720,9 @@ class Theatre { if (this.speakingAs != id) { this.speakingAs = id; KHelpers.addClass(navItem, "theatre-control-nav-bar-item-speakingas"); - TweenMax.to(Theatre.instance.theatreNavBar, 0.4, { scrollTo: { x: navItem.offsetLeft, offsetX: Theatre.instance.theatreNavBar.offsetWidth / 2 } }); + TweenMax.to(Theatre.instance.theatreNavBar, 0.4, { + scrollTo: { x: navItem.offsetLeft, offsetX: Theatre.instance.theatreNavBar.offsetWidth / 2 }, + }); // add label pulse insert.label.tint = 0xffffff; @@ -4732,7 +4781,9 @@ class Theatre { this.speakingAs = id; KHelpers.addClass(navItem, "theatre-control-nav-bar-item-speakingas"); - TweenMax.to(Theatre.instance.theatreNavBar, 0.4, { scrollTo: { x: navItem.offsetLeft, offsetX: Theatre.instance.theatreNavBar.offsetWidth / 2 } }); + TweenMax.to(Theatre.instance.theatreNavBar, 0.4, { + scrollTo: { x: navItem.offsetLeft, offsetX: Theatre.instance.theatreNavBar.offsetWidth / 2 }, + }); window.setTimeout(() => { insert = this.getInsertById(id); @@ -5036,7 +5087,12 @@ class Theatre { let textFlyin = Theatre.FLYIN_ANIMS; let textStanding = Theatre.STANDING_ANIMS; let sideBar = document.getElementById("sidebar"); - renderTemplate("modules/theatre/app/templates/emote_menu.html", { emotes, textFlyin, textStanding, fonts }).then((template) => { + renderTemplate("modules/theatre/app/templates/emote_menu.html", { + emotes, + textFlyin, + textStanding, + fonts, + }).then((template) => { if (Theatre.DEBUG) console.log("emote window template rendered"); Theatre.instance.theatreEmoteMenu.style.top = `${Theatre.instance.theatreControls.offsetTop - 410}px`; Theatre.instance.theatreEmoteMenu.innerHTML = template; @@ -5527,9 +5583,9 @@ class Theatre { ui.notifications.info(game.i18n.localize("Theatre.NotYet")); /* if (KHelpers.hasClass(ev.currentTarget,"theatre-control-small-btn-down")) { - KHelpers.removeClass(ev.currentTarget,"theatre-control-small-btn-down"); + KHelpers.removeClass(ev.currentTarget,"theatre-control-small-btn-down"); } else { - KHelpers.addClass(ev.currentTarget,"theatre-control-small-btn-down"); + KHelpers.addClass(ev.currentTarget,"theatre-control-small-btn-down"); ui.notifications.info(game.i18n.localize("Theatre.NotYet")); } */ @@ -5825,7 +5881,7 @@ class Theatre { ev.stopPropagation(); } else if (ev.altKey) { let actor = game.actors.get(id.replace("theatre-", "")); - Theatre.addToNavBar(actor.data); + Theatre.addToNavBar(actor); } else if (Theatre.instance.swapTarget) { if (Theatre.instance.swapTarget != id) { //Theatre.instance.swapInsertsById(id,Theatre.instance.swapTarget); @@ -6620,12 +6676,10 @@ class Theatre { */ static getActorEmotes(actorId, disableDefault) { let actor = game.actors.get(actorId); - let data, ae, de, re; - - if (actor) data = actor.data; + let ae, de, re; - if (data && data.flags.theatre) { - ae = data.flags.theatre.emotes; + if (actor && actor.flags.theatre) { + ae = actor.flags.theatre.emotes; if (disableDefault) { re = ae; } else { @@ -6649,14 +6703,12 @@ class Theatre { */ static getActorRiggingResources(actorId) { let actor = game.actors.get(actorId); - let data, ar, dr, rr; - - if (actor) data = actor.data; + let ar, dr, rr; dr = Theatre.getDefaultRiggingResources(); - if (data && data.flags.theatre && data.flags.theatre.rigging && data.flags.theatre.rigging.resources) { - ar = data.flags.theatre.rigging.resources; - rr = dr.concat(ar); + if (actor && actor.flags.theatre && actor.flags.theatre.rigging && actor.flags.theatre.rigging.resources) { + ar = actor.flags.theatre.rigging.resources; + rr = defaultRiggingResources.concat(ar); } else rr = dr; return rr; @@ -6794,12 +6846,30 @@ class Theatre { rigging: { animations: [ { name: "happytears", syntax: "happytears|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, - { name: "line_a", syntax: "line|0.5;(ease:bounce);x:40%,35%;y:5%,0%;rotation:-20,-20|0.5;(repeat:-1,yoyo:true);scaleX:1,1.2;scaleY:1,1.5" }, - { name: "line_b", syntax: "line|0.5;(ease:bounce);x:30%,20%;y:15%,12%;rotation:-65,-65|0.5;(repeat:-1,yoyo:true);scaleX:1,1.2;scaleY:1,1.5" }, - { name: "line_c", syntax: "line|0.5;(ease:bounce);x:60%,65%;y:5%,0%;rotation:20,20|0.5;(repeat:-1,yoyo:true);scaleX:1,1.2;scaleY:1,1.5" }, - { name: "line_d", syntax: "line|0.5;(ease:bounce);x:70%,80%;y:15%,12%;rotation:65,65|0.5;(repeat:-1,yoyo:true);scaleX:1,1.2;scaleY:1,1.5" }, - { name: "tears_a", syntax: "tears|0.5;(repeat:-1,repeatDelay:1.7);x:60%,110%;y:25%,40%;rotation:-30,-30;alpha:0.5,0|0;scaleX:-1,-1" }, - { name: "tears_b", syntax: "tears|0.5;(repeat:-1,repeatDelay:0.8);x:40%,-10%;y:25%,40%;rotation:30,30;alpha:0.5,0" }, + { + name: "line_a", + syntax: "line|0.5;(ease:bounce);x:40%,35%;y:5%,0%;rotation:-20,-20|0.5;(repeat:-1,yoyo:true);scaleX:1,1.2;scaleY:1,1.5", + }, + { + name: "line_b", + syntax: "line|0.5;(ease:bounce);x:30%,20%;y:15%,12%;rotation:-65,-65|0.5;(repeat:-1,yoyo:true);scaleX:1,1.2;scaleY:1,1.5", + }, + { + name: "line_c", + syntax: "line|0.5;(ease:bounce);x:60%,65%;y:5%,0%;rotation:20,20|0.5;(repeat:-1,yoyo:true);scaleX:1,1.2;scaleY:1,1.5", + }, + { + name: "line_d", + syntax: "line|0.5;(ease:bounce);x:70%,80%;y:15%,12%;rotation:65,65|0.5;(repeat:-1,yoyo:true);scaleX:1,1.2;scaleY:1,1.5", + }, + { + name: "tears_a", + syntax: "tears|0.5;(repeat:-1,repeatDelay:1.7);x:60%,110%;y:25%,40%;rotation:-30,-30;alpha:0.5,0|0;scaleX:-1,-1", + }, + { + name: "tears_b", + syntax: "tears|0.5;(repeat:-1,repeatDelay:0.8);x:40%,-10%;y:25%,40%;rotation:30,30;alpha:0.5,0", + }, ], }, }, @@ -6832,18 +6902,54 @@ class Theatre { rigging: { animations: [ { name: "sad", syntax: "sad|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, - { name: "swirl_a", syntax: "swirl|0.5;(ease:power4);x:110%,75%;y:0%,10%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, - { name: "swirl_b", syntax: "swirl|0.5;(ease:power4);x:110%,65%;y:0%,40%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, - { name: "swirl_c", syntax: "swirl|0.5;(ease:power4);x:110%,90%;y:110%,50%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, - { name: "swirl_d", syntax: "swirl|0.5;(ease:power4);x:110%,85%;y:110%,70%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, - { name: "swirl_e", syntax: "swirl|0.5;(ease:power4);x:-10%,25%;y:0%,15%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, - { name: "swirl_f", syntax: "swirl|0.5;(ease:power4);x:-10%,15%;y:0%,38%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, - { name: "swirl_g", syntax: "swirl|0.5;(ease:power4);x:-10%,20%;y:110%,55%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, - { name: "swirl_h", syntax: "swirl|0.5;(ease:power4);x:-10%,35%;y:110%,67%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, - { name: "swirl_i", syntax: "swirl|0.5;(ease:power4);x:-10%,10%;y:110%,85%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, - { name: "swirl_j", syntax: "swirl|0.5;(ease:power4);x:-10%,45%;y:110%,95%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, - { name: "swirl_k", syntax: "swirl|0.5;(ease:power4);x:110%,95%;y:110%,90%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, - { name: "swirl_l", syntax: "swirl|0.5;(ease:power4);x:110%,70%;y:110%,82%;alpha:0,1|1;(repeat:-1);rotation:0,360" }, + { + name: "swirl_a", + syntax: "swirl|0.5;(ease:power4);x:110%,75%;y:0%,10%;alpha:0,1|1;(repeat:-1);rotation:0,360", + }, + { + name: "swirl_b", + syntax: "swirl|0.5;(ease:power4);x:110%,65%;y:0%,40%;alpha:0,1|1;(repeat:-1);rotation:0,360", + }, + { + name: "swirl_c", + syntax: "swirl|0.5;(ease:power4);x:110%,90%;y:110%,50%;alpha:0,1|1;(repeat:-1);rotation:0,360", + }, + { + name: "swirl_d", + syntax: "swirl|0.5;(ease:power4);x:110%,85%;y:110%,70%;alpha:0,1|1;(repeat:-1);rotation:0,360", + }, + { + name: "swirl_e", + syntax: "swirl|0.5;(ease:power4);x:-10%,25%;y:0%,15%;alpha:0,1|1;(repeat:-1);rotation:0,360", + }, + { + name: "swirl_f", + syntax: "swirl|0.5;(ease:power4);x:-10%,15%;y:0%,38%;alpha:0,1|1;(repeat:-1);rotation:0,360", + }, + { + name: "swirl_g", + syntax: "swirl|0.5;(ease:power4);x:-10%,20%;y:110%,55%;alpha:0,1|1;(repeat:-1);rotation:0,360", + }, + { + name: "swirl_h", + syntax: "swirl|0.5;(ease:power4);x:-10%,35%;y:110%,67%;alpha:0,1|1;(repeat:-1);rotation:0,360", + }, + { + name: "swirl_i", + syntax: "swirl|0.5;(ease:power4);x:-10%,10%;y:110%,85%;alpha:0,1|1;(repeat:-1);rotation:0,360", + }, + { + name: "swirl_j", + syntax: "swirl|0.5;(ease:power4);x:-10%,45%;y:110%,95%;alpha:0,1|1;(repeat:-1);rotation:0,360", + }, + { + name: "swirl_k", + syntax: "swirl|0.5;(ease:power4);x:110%,95%;y:110%,90%;alpha:0,1|1;(repeat:-1);rotation:0,360", + }, + { + name: "swirl_l", + syntax: "swirl|0.5;(ease:power4);x:110%,70%;y:110%,82%;alpha:0,1|1;(repeat:-1);rotation:0,360", + }, ], }, }, @@ -6855,12 +6961,30 @@ class Theatre { rigging: { animations: [ { name: "cry", syntax: "cry|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, - { name: "tears_a", syntax: "tears|0.5;(repeat:-1,repeatDelay:0.7);x:60%,110%;y:25%,40%;rotation:-30,-30;alpha:0.5,0|0;scaleX:-1,-1" }, - { name: "tears_b", syntax: "tears|0.5;(repeat:-1,repeatDelay:0.3);x:40%,-10%;y:25%,40%;rotation:30,30;alpha:0.5,0" }, - { name: "tears_c", syntax: "tears|0.5;(repeat:-1,repeatDelay:0.8);x:60%,90%;y:25%,50%;rotation:-10,-10;alpha:0.5,0|0;scaleX:-1,-1" }, - { name: "tears_d", syntax: "tears|0.5;(repeat:-1,repeatDelay:1.0);x:40%,10%;y:25%,50%;rotation:10,10;alpha:0.5,0" }, - { name: "tears_e", syntax: "tears|0.5;(repeat:-1,repeatDelay:0.2);x:60%,90%;y:25%,30%;rotation:-50,-50;alpha:0.5,0|0;scaleX:-1,-1" }, - { name: "tears_f", syntax: "tears|0.5;(repeat:-1,repeatDelay:1.2);x:40%,10%;y:25%,30%;rotation:50,50;alpha:0.5,0" }, + { + name: "tears_a", + syntax: "tears|0.5;(repeat:-1,repeatDelay:0.7);x:60%,110%;y:25%,40%;rotation:-30,-30;alpha:0.5,0|0;scaleX:-1,-1", + }, + { + name: "tears_b", + syntax: "tears|0.5;(repeat:-1,repeatDelay:0.3);x:40%,-10%;y:25%,40%;rotation:30,30;alpha:0.5,0", + }, + { + name: "tears_c", + syntax: "tears|0.5;(repeat:-1,repeatDelay:0.8);x:60%,90%;y:25%,50%;rotation:-10,-10;alpha:0.5,0|0;scaleX:-1,-1", + }, + { + name: "tears_d", + syntax: "tears|0.5;(repeat:-1,repeatDelay:1.0);x:40%,10%;y:25%,50%;rotation:10,10;alpha:0.5,0", + }, + { + name: "tears_e", + syntax: "tears|0.5;(repeat:-1,repeatDelay:0.2);x:60%,90%;y:25%,30%;rotation:-50,-50;alpha:0.5,0|0;scaleX:-1,-1", + }, + { + name: "tears_f", + syntax: "tears|0.5;(repeat:-1,repeatDelay:1.2);x:40%,10%;y:25%,30%;rotation:50,50;alpha:0.5,0", + }, ], }, }, @@ -6882,7 +7006,10 @@ class Theatre { rigging: { animations: [ { name: "annoyed", syntax: "annoyed|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, - { name: "ziggy", syntax: "ziggy|0;x:25%,25%;y:20%,20%|0.25;(repeat:-1,yoyo:true);rotation:-2,2" }, + { + name: "ziggy", + syntax: "ziggy|0;x:25%,25%;y:20%,20%|0.25;(repeat:-1,yoyo:true);rotation:-2,2", + }, { name: "ziggy_2", syntax: "ziggy|1;(repeat:-1,delay:1,repeatDelay:2);scaleX:1,2;scaleY:1,2;x:25%,25%;y:20%,20%;alpha:0.5,0|0.25;(repeat:-1,yoyo:true);rotation:0,5", @@ -6899,7 +7026,10 @@ class Theatre { rigging: { animations: [ { name: "frustrated", syntax: "frustrated|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, - { name: "veins", syntax: "veins|0.5;x:45%,45%;y:10%,10%;alpha:0,1|1;(repeat:-1,yoyo:true,ease:bounce);scaleX:0.7,1;scaleY:0.7,1" }, + { + name: "veins", + syntax: "veins|0.5;x:45%,45%;y:10%,10%;alpha:0,1|1;(repeat:-1,yoyo:true,ease:bounce);scaleX:0.7,1;scaleY:0.7,1", + }, ], }, }, @@ -6915,10 +7045,22 @@ class Theatre { name: "veins", syntax: "veins_red|0.5;x:45%,45%;y:10%,10%;alpha:0,1|1;(repeat:-1,yoyo:true,ease:elastic);scaleX:0.5,1;scaleY:0.5,1|0.25;(repeat:-1,yoyo:true);rotation:0,10", }, - { name: "puff_a", syntax: "puff|0;x:80%,80%;y:15%,15%;rotation:0,0|1;(repeat:-1,delay:1,yoyo:true,ease:power4);scaleX:0.3,1;scaleY:0.3,1;alpha:0,0.5" }, - { name: "puff_b", syntax: "puff|0;x:20%,20%;y:15%,15%;rotation:0,0|1;(repeat:-1,delay:1.5,yoyo:true,ease:power4);scaleX:-0.3,-1;scaleY:0.3,1;alpha:0,0.5" }, - { name: "puff_c", syntax: "puff|0;x:70%,70%;y:5%,5%;rotation:330,330|1;(repeat:-1,delay:2,yoyo:true,ease:power4);scaleX:0.3,1;scaleY:0.3,1;alpha:0,0.5" }, - { name: "puff_d", syntax: "puff|0;x:30%,30%;y:5%,5%;rotation:30,30|1;(repeat:-1,delay:2.5,yoyo:true,ease:power4);scaleX:-0.3,-1;scaleY:0.3,1;alpha:0,0.5" }, + { + name: "puff_a", + syntax: "puff|0;x:80%,80%;y:15%,15%;rotation:0,0|1;(repeat:-1,delay:1,yoyo:true,ease:power4);scaleX:0.3,1;scaleY:0.3,1;alpha:0,0.5", + }, + { + name: "puff_b", + syntax: "puff|0;x:20%,20%;y:15%,15%;rotation:0,0|1;(repeat:-1,delay:1.5,yoyo:true,ease:power4);scaleX:-0.3,-1;scaleY:0.3,1;alpha:0,0.5", + }, + { + name: "puff_c", + syntax: "puff|0;x:70%,70%;y:5%,5%;rotation:330,330|1;(repeat:-1,delay:2,yoyo:true,ease:power4);scaleX:0.3,1;scaleY:0.3,1;alpha:0,0.5", + }, + { + name: "puff_d", + syntax: "puff|0;x:30%,30%;y:5%,5%;rotation:30,30|1;(repeat:-1,delay:2.5,yoyo:true,ease:power4);scaleX:-0.3,-1;scaleY:0.3,1;alpha:0,0.5", + }, ], }, }, @@ -6944,8 +7086,14 @@ class Theatre { label: game.i18n.localize("Theatre.Emote.LaughingSquint"), rigging: { animations: [ - { name: "laughingsquint", syntax: "laughingsquint|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, - { name: "loud", syntax: "loud|0.5;x:25%,25%;y:20%,20%;alpha:0,1|0.5;(ease:bounce);scaleX:0.1,1;scaleY:0.1,1|0.125;(repeat:-1,yoyo:true);rotation:-1,1" }, + { + name: "laughingsquint", + syntax: "laughingsquint|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1", + }, + { + name: "loud", + syntax: "loud|0.5;x:25%,25%;y:20%,20%;alpha:0,1|0.5;(ease:bounce);scaleX:0.1,1;scaleY:0.1,1|0.125;(repeat:-1,yoyo:true);rotation:-1,1", + }, ], }, }, @@ -6957,12 +7105,30 @@ class Theatre { rigging: { animations: [ { name: "rofl", syntax: "rofl|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, - { name: "loud_a", syntax: "loud|0.5;(ease:bounce);x:20%,20%;y:20%,20%;scaleX:0.1,1;scaleY:0.1,1|0.125;(repeat:-1,yoyo:true);rotation:-2,2" }, - { name: "loud_b", syntax: "loud|0.5;(ease:bounce);x:80%,80%;y:20%,20%;scaleX:-0.1,-1;scaleY:0.1,1|0.125;(repeat:-1,yoyo:true);rotation:-2,2" }, - { name: "loud_c", syntax: "loud|0;x:20%,20%;y:20%,20%|0.125;(repeat:-1,yoyo:true);rotation:-2,2|1;(repeat:-1);scaleX:1,1.5;scaleY:1,2;alpha:0.25,0" }, - { name: "loud_d", syntax: "loud|0;x:80%,80%;y:20%,20%|0.125;(repeat:-1,yoyo:true);rotation:-2,2|1;(repeat:-1);scaleX:-1,-1.5;scaleY:1,2;alpha:0.25,0" }, - { name: "tears_a", syntax: "tears|0.5;(repeat:-1,repeatDelay:1.7);x:60%,110%;y:25%,40%;rotation:-30,-30;alpha:0.5,0|0;scaleX:-1,-1" }, - { name: "tears_b", syntax: "tears|0.5;(repeat:-1,repeatDelay:0.8);x:40%,-10%;y:25%,40%;rotation:30,30;alpha:0.5,0" }, + { + name: "loud_a", + syntax: "loud|0.5;(ease:bounce);x:20%,20%;y:20%,20%;scaleX:0.1,1;scaleY:0.1,1|0.125;(repeat:-1,yoyo:true);rotation:-2,2", + }, + { + name: "loud_b", + syntax: "loud|0.5;(ease:bounce);x:80%,80%;y:20%,20%;scaleX:-0.1,-1;scaleY:0.1,1|0.125;(repeat:-1,yoyo:true);rotation:-2,2", + }, + { + name: "loud_c", + syntax: "loud|0;x:20%,20%;y:20%,20%|0.125;(repeat:-1,yoyo:true);rotation:-2,2|1;(repeat:-1);scaleX:1,1.5;scaleY:1,2;alpha:0.25,0", + }, + { + name: "loud_d", + syntax: "loud|0;x:80%,80%;y:20%,20%|0.125;(repeat:-1,yoyo:true);rotation:-2,2|1;(repeat:-1);scaleX:-1,-1.5;scaleY:1,2;alpha:0.25,0", + }, + { + name: "tears_a", + syntax: "tears|0.5;(repeat:-1,repeatDelay:1.7);x:60%,110%;y:25%,40%;rotation:-30,-30;alpha:0.5,0|0;scaleX:-1,-1", + }, + { + name: "tears_b", + syntax: "tears|0.5;(repeat:-1,repeatDelay:0.8);x:40%,-10%;y:25%,40%;rotation:30,30;alpha:0.5,0", + }, ], }, }, @@ -6986,7 +7152,10 @@ class Theatre { rigging: { animations: [ { name: "surprised", syntax: "surprised|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, - { name: "notice", syntax: "notice|0.5;x:25%,25%;y:20%,20%;alpha:0,1|0.5;(ease:bounce);scaleX:0.1,1;scaleY:0.1,1" }, + { + name: "notice", + syntax: "notice|0.5;x:25%,25%;y:20%,20%;alpha:0,1|0.5;(ease:bounce);scaleX:0.1,1;scaleY:0.1,1", + }, ], }, }, @@ -6998,18 +7167,54 @@ class Theatre { rigging: { animations: [ { name: "awe-struck", syntax: "awe-struck|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, - { name: "glimmer_a", syntax: "glimmer|0.5;x:10%,10%;y:58%,58%|0.5;(delay:0.2,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, - { name: "glimmer_b", syntax: "glimmer|0.5;x:85%,85%;y:20%,20%|0.5;(delay:0.3,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, - { name: "glimmer_c", syntax: "glimmer|0.5;x:40%,40%;y:45%,45%|0.5;(delay:0.5,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, - { name: "glimmer_d", syntax: "glimmer|0.5;x:35%,35%;y:30%,30%|0.5;(delay:0.6,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, - { name: "glimmer_e", syntax: "glimmer|0.5;x:65%,65%;y:35%,35%|0.5;(delay:0.4,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, - { name: "glimmer_f", syntax: "glimmer|0.5;x:80%,80%;y:50%,50%|0.5;(delay:0.1,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, - { name: "glimmer_g", syntax: "glimmer|0.5;x:16%,16%;y:81%,81%|0.5;(delay:0.8,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, - { name: "glimmer_h", syntax: "glimmer|0.5;x:55%,55%;y:64%,64%|0.5;(delay:0.9,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, - { name: "glimmer_i", syntax: "glimmer|0.5;x:44%,44%;y:95%,95%|0.5;(delay:0.7,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, - { name: "glimmer_j", syntax: "glimmer|0.5;x:67%,67%;y:84%,84%|0.5;(delay:0.35,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, - { name: "glimmer_k", syntax: "glimmer|0.5;x:44%,44%;y:70%,70%|0.5;(delay:0,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, - { name: "glimmer_l", syntax: "glimmer|0.5;x:20%,20%;y:23%,23%|0.5;(delay:0.65,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1" }, + { + name: "glimmer_a", + syntax: "glimmer|0.5;x:10%,10%;y:58%,58%|0.5;(delay:0.2,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "glimmer_b", + syntax: "glimmer|0.5;x:85%,85%;y:20%,20%|0.5;(delay:0.3,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "glimmer_c", + syntax: "glimmer|0.5;x:40%,40%;y:45%,45%|0.5;(delay:0.5,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "glimmer_d", + syntax: "glimmer|0.5;x:35%,35%;y:30%,30%|0.5;(delay:0.6,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "glimmer_e", + syntax: "glimmer|0.5;x:65%,65%;y:35%,35%|0.5;(delay:0.4,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "glimmer_f", + syntax: "glimmer|0.5;x:80%,80%;y:50%,50%|0.5;(delay:0.1,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "glimmer_g", + syntax: "glimmer|0.5;x:16%,16%;y:81%,81%|0.5;(delay:0.8,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "glimmer_h", + syntax: "glimmer|0.5;x:55%,55%;y:64%,64%|0.5;(delay:0.9,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "glimmer_i", + syntax: "glimmer|0.5;x:44%,44%;y:95%,95%|0.5;(delay:0.7,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "glimmer_j", + syntax: "glimmer|0.5;x:67%,67%;y:84%,84%|0.5;(delay:0.35,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "glimmer_k", + syntax: "glimmer|0.5;x:44%,44%;y:70%,70%|0.5;(delay:0,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "glimmer_l", + syntax: "glimmer|0.5;x:20%,20%;y:23%,23%|0.5;(delay:0.65,repeat:-1,yoyo:true);scaleX:0.0,1;scaleY:0.0,1", + }, ], }, }, @@ -7107,7 +7312,10 @@ class Theatre { rigging: { animations: [ { name: "thinking", syntax: "thinking|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, - { name: "thoughtbubble", syntax: "thoughtbubble|0.5;(ease:power3);x:25%,25%;y:10%,10%;alpha:0,1|0.5;(repeat:-1,yoyo:true);scaleX:0.95,1;scaleY:0.95,1" }, + { + name: "thoughtbubble", + syntax: "thoughtbubble|0.5;(ease:power3);x:25%,25%;y:10%,10%;alpha:0,1|0.5;(repeat:-1,yoyo:true);scaleX:0.95,1;scaleY:0.95,1", + }, { name: "bubbledot_a", syntax: "bubbledot|0.5;(ease:power3);x:28%,28%;y:18%,18%;alpha:0,1|1;(repeat:-1,yoyo:true,repeatDelay:0.3);scaleX:0.5,1;scaleY:0.5,1|5;(repeat:-1);rotation:0,360", @@ -7163,7 +7371,10 @@ class Theatre { rigging: { animations: [ { name: "meh", syntax: "meh|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, - { name: "sigh", syntax: "sigh|3;(ease:power2);x:30%,10%;y:25%,45%;alpha:1,0;rotation:225,225;scaleX:1,1.5;scaleY:1,1.5" }, + { + name: "sigh", + syntax: "sigh|3;(ease:power2);x:30%,10%;y:25%,45%;alpha:1,0;rotation:225,225;scaleX:1,1.5;scaleY:1,1.5", + }, ], }, }, @@ -7185,9 +7396,18 @@ class Theatre { rigging: { animations: [ { name: "wink", syntax: "wink|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, - { name: "kawaii_a", syntax: "star|4;(ease:expo);x:45%,-10%;y:25%,25%;alpha:1,0|2;(repeat:4);rotation:0,360" }, - { name: "kawaii_b", syntax: "star|3;(ease:expo);x:45%,10%;y:25%,12%;alpha:1,0|2;(repeat:4);rotation:0,360" }, - { name: "kawaii_c", syntax: "star|3;(ease:expo);x:45%,10%;y:25%,38%;alpha:1,0|2;(repeat:4);rotation:0,360" }, + { + name: "kawaii_a", + syntax: "star|4;(ease:expo);x:45%,-10%;y:25%,25%;alpha:1,0|2;(repeat:4);rotation:0,360", + }, + { + name: "kawaii_b", + syntax: "star|3;(ease:expo);x:45%,10%;y:25%,12%;alpha:1,0|2;(repeat:4);rotation:0,360", + }, + { + name: "kawaii_c", + syntax: "star|3;(ease:expo);x:45%,10%;y:25%,38%;alpha:1,0|2;(repeat:4);rotation:0,360", + }, ], }, }, @@ -7199,7 +7419,10 @@ class Theatre { rigging: { animations: [ { name: "tongue", syntax: "tongue|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, - { name: "kawaii", syntax: "star|4;(ease:expo,delay:2);x:30%,30%;y:25%,25%;alpha:1,0;scaleX:1.3,0.1;scaleY:1.3,0.1|2;(repeat:4);rotation:0,360" }, + { + name: "kawaii", + syntax: "star|4;(ease:expo,delay:2);x:30%,30%;y:25%,25%;alpha:1,0;scaleX:1.3,0.1;scaleY:1.3,0.1|2;(repeat:4);rotation:0,360", + }, ], }, }, @@ -7211,14 +7434,38 @@ class Theatre { rigging: { animations: [ { name: "playful", syntax: "playful|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, - { name: "kawaii_a", syntax: "star|3;(ease:expo);x:40%,-10%;y:25%,-15%;alpha:1,0|2;(repeat:4);rotation:0,360" }, - { name: "kawaii_b", syntax: "star|4;(ease:expo);x:40%,-40%;y:25%,30%;alpha:1,0|2;(repeat:4);rotation:0,360" }, - { name: "kawaii_c", syntax: "star|3;(ease:expo);x:40%,-10%;y:25%,55%;alpha:1,0|2;(repeat:4);rotation:0,360" }, - { name: "kawaii_d", syntax: "star|3;(ease:expo);x:60%,110%;y:25%,-15%;alpha:1,0|2;(repeat:4);rotation:0,360" }, - { name: "kawaii_e", syntax: "star|4;(ease:expo);x:60%,140%;y:25%,30%;alpha:1,0|2;(repeat:4);rotation:0,360" }, - { name: "kawaii_f", syntax: "star|3;(ease:expo);x:60%,110%;y:25%,55%;alpha:1,0|2;(repeat:4);rotation:0,360" }, - { name: "kawaii_g", syntax: "star|4;(ease:expo);x:50%,50%;y:15%,-35%;alpha:1,0|2;(repeat:4);rotation:0,360" }, - { name: "kawaii_h", syntax: "star|4;(ease:expo);x:50%,50%;y:35%,85%;alpha:1,0|2;(repeat:4);rotation:0,360" }, + { + name: "kawaii_a", + syntax: "star|3;(ease:expo);x:40%,-10%;y:25%,-15%;alpha:1,0|2;(repeat:4);rotation:0,360", + }, + { + name: "kawaii_b", + syntax: "star|4;(ease:expo);x:40%,-40%;y:25%,30%;alpha:1,0|2;(repeat:4);rotation:0,360", + }, + { + name: "kawaii_c", + syntax: "star|3;(ease:expo);x:40%,-10%;y:25%,55%;alpha:1,0|2;(repeat:4);rotation:0,360", + }, + { + name: "kawaii_d", + syntax: "star|3;(ease:expo);x:60%,110%;y:25%,-15%;alpha:1,0|2;(repeat:4);rotation:0,360", + }, + { + name: "kawaii_e", + syntax: "star|4;(ease:expo);x:60%,140%;y:25%,30%;alpha:1,0|2;(repeat:4);rotation:0,360", + }, + { + name: "kawaii_f", + syntax: "star|3;(ease:expo);x:60%,110%;y:25%,55%;alpha:1,0|2;(repeat:4);rotation:0,360", + }, + { + name: "kawaii_g", + syntax: "star|4;(ease:expo);x:50%,50%;y:15%,-35%;alpha:1,0|2;(repeat:4);rotation:0,360", + }, + { + name: "kawaii_h", + syntax: "star|4;(ease:expo);x:50%,50%;y:35%,85%;alpha:1,0|2;(repeat:4);rotation:0,360", + }, ], }, }, @@ -7232,21 +7479,66 @@ class Theatre { animations: [ { name: "evil", syntax: "evil|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, { name: "shroud", syntax: "darkness|0;x:50%,50%;y:50%,50%" }, - { name: "miasma_a", syntax: "miasma|0;x:25%,25%;y:78%,78%|3;(repeat:-1,delay:0.3);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, - { name: "miasma_b", syntax: "miasma|0;x:73%,73%;y:68%,68%|3;(repeat:-1,delay:1.3);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, - { name: "miasma_c", syntax: "miasma|0;x:15%,15%;y:60%,60%|3;(repeat:-1,delay:0.8);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, - { name: "miasma_d", syntax: "miasma|0;x:45%,45%;y:85%,85%|3;(repeat:-1,delay:2.6);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, - { name: "miasma_e", syntax: "miasma|0;x:90%,90%;y:80%,80%|3;(repeat:-1,delay:3.5);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, - { name: "miasma_f", syntax: "miasma|0;x:55%,55%;y:60%,60%|3;(repeat:-1,delay:2.1);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, - { name: "miasma_g", syntax: "miasma|0;x:10%,10%;y:90%,90%|3;(repeat:-1,delay:3.8);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, - { name: "miasma_h", syntax: "miasma|0;x:95%,95%;y:70%,70%|3;(repeat:-1,delay:1.8);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, - { name: "miasma_i", syntax: "miasma|0;x:50%,50%;y:72%,72%|3;(repeat:-1,delay:5.8);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, - { name: "miasma_j", syntax: "miasma|0;x:10%,10%;y:66%,66%|3;(repeat:-1,delay:3.6);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, - { name: "miasma_k", syntax: "miasma|0;x:3%,3%;y:88%,88%|3;(repeat:-1,delay:2.2);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, - { name: "miasma_l", syntax: "miasma|0;x:78%,78%;y:75%,75%|3;(repeat:-1,delay:1.7);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, - { name: "miasma_m", syntax: "miasma|0;x:65%,65%;y:98%,98%|3;(repeat:-1,delay:.7);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, - { name: "miasma_n", syntax: "miasma|0;x:33%,33%;y:78%,78%|3;(repeat:-1,delay:4.4);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, - { name: "miasma_o", syntax: "miasma|0;x:80%,80%;y:92%,92%|3;(repeat:-1,delay:5.2);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1" }, + { + name: "miasma_a", + syntax: "miasma|0;x:25%,25%;y:78%,78%|3;(repeat:-1,delay:0.3);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "miasma_b", + syntax: "miasma|0;x:73%,73%;y:68%,68%|3;(repeat:-1,delay:1.3);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "miasma_c", + syntax: "miasma|0;x:15%,15%;y:60%,60%|3;(repeat:-1,delay:0.8);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "miasma_d", + syntax: "miasma|0;x:45%,45%;y:85%,85%|3;(repeat:-1,delay:2.6);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "miasma_e", + syntax: "miasma|0;x:90%,90%;y:80%,80%|3;(repeat:-1,delay:3.5);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "miasma_f", + syntax: "miasma|0;x:55%,55%;y:60%,60%|3;(repeat:-1,delay:2.1);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "miasma_g", + syntax: "miasma|0;x:10%,10%;y:90%,90%|3;(repeat:-1,delay:3.8);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "miasma_h", + syntax: "miasma|0;x:95%,95%;y:70%,70%|3;(repeat:-1,delay:1.8);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "miasma_i", + syntax: "miasma|0;x:50%,50%;y:72%,72%|3;(repeat:-1,delay:5.8);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "miasma_j", + syntax: "miasma|0;x:10%,10%;y:66%,66%|3;(repeat:-1,delay:3.6);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "miasma_k", + syntax: "miasma|0;x:3%,3%;y:88%,88%|3;(repeat:-1,delay:2.2);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "miasma_l", + syntax: "miasma|0;x:78%,78%;y:75%,75%|3;(repeat:-1,delay:1.7);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "miasma_m", + syntax: "miasma|0;x:65%,65%;y:98%,98%|3;(repeat:-1,delay:.7);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "miasma_n", + syntax: "miasma|0;x:33%,33%;y:78%,78%|3;(repeat:-1,delay:4.4);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1", + }, + { + name: "miasma_o", + syntax: "miasma|0;x:80%,80%;y:92%,92%|3;(repeat:-1,delay:5.2);alpha:1,0;scaleX:0.0,1;scaleY:0.0,1", + }, ], }, }, @@ -7259,7 +7551,10 @@ class Theatre { rigging: { animations: [ { name: "innocent", syntax: "innocent|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, - { name: "halo", syntax: "halo|2;(ease:power2);x:50%,50%;alpha:0,1|2;(ease:sine,repeat:-1,yoyo:true,yoyoEase:sine);y:-3%,-5%" }, + { + name: "halo", + syntax: "halo|2;(ease:power2);x:50%,50%;alpha:0,1|2;(ease:sine,repeat:-1,yoyo:true,yoyoEase:sine);y:-3%,-5%", + }, ], }, }, @@ -7295,17 +7590,44 @@ class Theatre { rigging: { animations: [ { name: "panic", syntax: "panic|1;(ease:elastic);x:80%,80%;y:0%,25%;alpha:0,1" }, - { name: "line_a", syntax: "linesteep|0;x:50%,50%;y:-10%,-10%|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1" }, + { + name: "line_a", + syntax: "linesteep|0;x:50%,50%;y:-10%,-10%|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1", + }, - { name: "line_b", syntax: "linesteep|0;x:35%,35%;y:-5%,-5%;rotation:-22.5,-22.5|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1" }, - { name: "line_c", syntax: "linesteep|0;x:15%,15%;y:5%,5%;rotation:-45,-45|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1" }, - { name: "line_d", syntax: "linesteep|0;x:0%,0%;y:20%,20%;rotation:-67.5,-67.5|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1" }, - { name: "line_e", syntax: "linesteep|0;x:-10%,-10%;y:30%,30%;rotation:-90,-90|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1" }, + { + name: "line_b", + syntax: "linesteep|0;x:35%,35%;y:-5%,-5%;rotation:-22.5,-22.5|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1", + }, + { + name: "line_c", + syntax: "linesteep|0;x:15%,15%;y:5%,5%;rotation:-45,-45|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1", + }, + { + name: "line_d", + syntax: "linesteep|0;x:0%,0%;y:20%,20%;rotation:-67.5,-67.5|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1", + }, + { + name: "line_e", + syntax: "linesteep|0;x:-10%,-10%;y:30%,30%;rotation:-90,-90|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1", + }, - { name: "line_f", syntax: "linesteep|0;x:65%,65%;y:-5%,-5%;rotation:22.5,22.5|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1" }, - { name: "line_g", syntax: "linesteep|0;x:85%,85%;y:5%,5%;rotation:45,45|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1" }, - { name: "line_h", syntax: "linesteep|0;x:100%,100%;y:20%,20%;rotation:67.5,67.5|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1" }, - { name: "line_i", syntax: "linesteep|0;x:110%,110%;y:30%,30%;rotation:90,90|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1" }, + { + name: "line_f", + syntax: "linesteep|0;x:65%,65%;y:-5%,-5%;rotation:22.5,22.5|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1", + }, + { + name: "line_g", + syntax: "linesteep|0;x:85%,85%;y:5%,5%;rotation:45,45|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1", + }, + { + name: "line_h", + syntax: "linesteep|0;x:100%,100%;y:20%,20%;rotation:67.5,67.5|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1", + }, + { + name: "line_i", + syntax: "linesteep|0;x:110%,110%;y:30%,30%;rotation:90,90|1;(repeat:-1,yoyo:true);scaleX:0.5,1;scaleY:0.5,1", + }, ], }, }, @@ -7776,8 +8098,8 @@ class Theatre { ev.preventDefault(); if (Theatre.DEBUG) console.log("Click Event on Configure Theatre!!!", actorSheet, actorSheet.actor, actorSheet.position); - if (!actorSheet.actor.data.flags.theatre) { - actorSheet.actor.data.flags.theatre = { baseinsert: "", name: "" }; + if (!actorSheet.actor.flags.theatre) { + actorSheet.actor.flags.theatre = { baseinsert: "", name: "" }; } new TheatreActorConfig(actorSheet.actor, { @@ -7822,9 +8144,9 @@ class Theatre { if (Theatre.DEBUG) console.log("actor is valid!"); // if already on stage, dont add it again // create nav-list-item - // set picture as actor.data.img + // set picture as actor.img // set attribute "theatre-id" to "theatre" + _id - // set attribute "insertImg" to object.data.flags.theatre.baseinsert or img if not specified + // set attribute "insertImg" to object.flags.theatre.baseinsert or img if not specified // add click handler to push it into the theatre bar, if it already exists on the bar, remove it // from the bar // add click handler logic to remove it from the stage diff --git a/app/js/TheatreActor.js b/app/js/TheatreActor.js index b0b9f3f..1c3c2d5 100644 --- a/app/js/TheatreActor.js +++ b/app/js/TheatreActor.js @@ -1,8 +1,8 @@ class TheatreActor { - constructor(actor, navElement) { - this.actor = actor; - this.navElement = navElement; - } + constructor(actor, navElement) { + this.actor = actor; + this.navElement = navElement; + } } /* diff --git a/app/js/TheatreActorConfig.js b/app/js/TheatreActorConfig.js index 8e4823c..48d76b2 100644 --- a/app/js/TheatreActorConfig.js +++ b/app/js/TheatreActorConfig.js @@ -31,7 +31,13 @@ class TheatreActorConfig extends FormApplication { constructor(object = {}, options = {}) { if (object._theatre_mod_configTab) { - options.tabs = [{ navSelector: ".tabs", contentSelector: ".theatre-config-contents", initial: object._theatre_mod_configTab }]; + options.tabs = [ + { + navSelector: ".tabs", + contentSelector: ".theatre-config-contents", + initial: object._theatre_mod_configTab, + }, + ]; if (object._theatre_mod_configTab === "emotes") { options.height = 775; } @@ -70,7 +76,7 @@ class TheatreActorConfig extends FormApplication { entityName: entityName, isGM: game.user.isGM, object: duplicate(this.object.data), - emote: Theatre.getActorEmotes(this.object.data._id), + emote: Theatre.getActorEmotes(this.object._id), options: this.options, }; } @@ -214,16 +220,16 @@ class TheatreActorConfig extends FormApplication { let baseInsert = formData["flags.theatre.baseinsert"]; let optAlign = formData["flags.theatre.optalign"]; let name = formData["flags.theatre.name"]; - let newBaseInsert = this.object.data.flags.theatre.baseinsert || (this.object.img ? this.object.img : "icons/mystery-man.png"); - let newName = this.object.data.flags.theatre.name || this.object.data.name; - let newAlign = this.object.data.flags.theatre.optalign || "top"; + let newBaseInsert = this.object.flags.theatre.baseinsert || (this.object.img ? this.object.img : "icons/mystery-man.png"); + let newName = this.object.flags.theatre.name || this.object.name; + let newAlign = this.object.flags.theatre.optalign || "top"; // update Navbar of the corresponding ID - let theatreId = `theatre-${this.object.data._id}`; + let theatreId = `theatre-${this.object._id}`; let navItem = Theatre.instance.getNavItemById(theatreId); let cImg = Theatre.instance.getTheatreCoverPortrait(); - if (baseInsert != this.object.data.flags.theatre.baseinsert) { + if (baseInsert != this.object.flags.theatre.baseinsert) { if (Theatre.DEBUG) console.log("baseinsert changed!"); insertDirty = true; newBaseInsert = baseInsert == "" ? (this.object.img ? this.object.img : "icons/mystery-man.png") : baseInsert; @@ -232,19 +238,19 @@ class TheatreActorConfig extends FormApplication { cImg.setAttribute("src", newBaseInsert); } } - if (optAlign != this.object.data.flags.theatre.optalign) { + if (optAlign != this.object.flags.theatre.optalign) { if (Theatre.DEBUG) console.log("optalign changed!"); insertDirty = true; newAlign = optAlign == "" ? "top" : optAlign; if (navItem) navItem.setAttribute("optalign", newAlign); } - if (name != this.object.data.flags.theatre.name) { + if (name != this.object.flags.theatre.name) { if (Theatre.DEBUG) console.log("name changed!"); insertDirty = true; - newName = name == "" ? this.object.data.name : name; + newName = name == "" ? this.object.name : name; if (navItem) { navItem.setAttribute("name", newName); - navItem.setAttribute("title", newName + (newName == this.object.data.name ? "" : ` (${this.object.data.name})`)); + navItem.setAttribute("title", newName + (newName == this.object.name ? "" : ` (${this.object.name})`)); } } // Add label information to update if it has data-edit @@ -281,10 +287,9 @@ class TheatreActorConfig extends FormApplication { let formBaseInsert = formData["flags.theatre.baseinsert"]; if (k.endsWith("insert") && !k.endsWith("baseinsert")) { if (formBaseInsert && formBaseInsert != "") resName = formBaseInsert; - else if (this.object.data.flags.theatre.baseinsert && this.object.data.flags.theatre.baseinsert != "") - resName = this.object.data.flags.theatre.baseinsert; - else resName = this.object.data.img ? this.object.data.img : "icons/mystery-man.png"; - } else resName = this.object.data.img ? this.object.data.img : "icons/mystery-man.png"; + else if (this.object.flags.theatre.baseinsert && this.object.flags.theatre.baseinsert != "") resName = this.object.flags.theatre.baseinsert; + else resName = this.object.img ? this.object.img : "icons/mystery-man.png"; + } else resName = this.object.img ? this.object.img : "icons/mystery-man.png"; } // ensure resource exists @@ -330,11 +335,10 @@ class TheatreActorConfig extends FormApplication { if (Theatre.DEBUG) console.log("RE-RENDERING with NEW texture resource %s ", newSrcImg); let resName = "icons/myster-man.png"; - if (insert.emote && this.object.data.flags.theatre.emotes[insert.emote].insert && this.object.data.flags.theatre.emotes[insert.emote].insert != "") - resName = this.object.data.flags.theatre.emotes[insert.emote].insert; - else if (this.object.data.flags.theatre.baseinsert && this.object.data.flags.theatre.baseinsert != "") - resName = this.object.data.flags.theatre.baseinsert; - else if (this.object.data.img && this.object.data.img != "") resName = this.object.data.img; + if (insert.emote && this.object.flags.theatre.emotes[insert.emote].insert && this.object.flags.theatre.emotes[insert.emote].insert != "") + resName = this.object.flags.theatre.emotes[insert.emote].insert; + else if (this.object.flags.theatre.baseinsert && this.object.flags.theatre.baseinsert != "") resName = this.object.flags.theatre.baseinsert; + else if (this.object.img && this.object.img != "") resName = this.object.img; // bubble up dataum from the update insert.optAlign = newAlign; @@ -365,10 +369,10 @@ class TheatreActorConfig extends FormApplication { if (insertDirty && insert) { if (Theatre.DEBUG) console.log("Insert is dirty, re-render it!"); let resName = "icons/myster-man.png"; - if (insert.emote && this.object.data.flags.theatre.emotes[insert.emote].insert && this.object.data.flags.theatre.emotes[insert.emote].insert != "") - resName = this.object.data.flags.theatre.emotes[insert.emote].insert; - else if (this.object.data.flags.theatre.baseinsert && this.object.data.flags.theatre.baseinsert != "") resName = this.object.data.flags.theatre.baseinsert; - else if (this.object.data.img && this.object.data.img != "") resName = this.object.data.img; + if (insert.emote && this.object.flags.theatre.emotes[insert.emote].insert && this.object.flags.theatre.emotes[insert.emote].insert != "") + resName = this.object.flags.theatre.emotes[insert.emote].insert; + else if (this.object.flags.theatre.baseinsert && this.object.flags.theatre.baseinsert != "") resName = this.object.flags.theatre.baseinsert; + else if (this.object.img && this.object.img != "") resName = this.object.img; // bubble up dataum from the update insert.optAlign = newAlign; @@ -423,9 +427,13 @@ class TheatreActorConfig extends FormApplication { let customIdx = customElems.length > 0 ? customElems[customElems.length - 1].sortidx + 1 : 1; let customObjElems = []; - for (let k in this.object.data.flags.theatre.emotes) { + for (let k in this.object.flags.theatre.emotes) { let eName = k; - if (eName && eName.startsWith("custom")) customObjElems.push({ sortidx: Number(eName.match(/\d+/)[0]), elem: this.object.data.flags.theatre.emotes[k] }); + if (eName && eName.startsWith("custom")) + customObjElems.push({ + sortidx: Number(eName.match(/\d+/)[0]), + elem: this.object.flags.theatre.emotes[k], + }); } // we grab max index, we don't care about possible missing indexes from removed custom emotes // so we'll just leave them as gaps diff --git a/app/js/theatre_main.js b/app/js/theatre_main.js index 0fe69f1..cea6aeb 100644 --- a/app/js/theatre_main.js +++ b/app/js/theatre_main.js @@ -221,39 +221,39 @@ Hooks.on("deleteCombat", function () { */ Hooks.on("preCreateChatMessage", function (chatMessage) { let chatData = { - speaker: {}, + speaker: { + actor: null, + scene: null, + flags: {}, + }, }; - if (Theatre.DEBUG) console.log("preCreateChatMessage", chatMessage.data); + if (Theatre.DEBUG) console.log("preCreateChatMessage", chatMessage); // If theatre isn't even ready, then just no if (!Theatre.instance) return; // make the message OOC if needed - if (!chatMessage.data.roll && $(theatre.theatreChatCover).hasClass("theatre-control-chat-cover-ooc")) { - const user = game.users.get(chatMessage.data.user.id); - chatData.speaker.alias = user.data.name; - chatData.speaker.actor = null; - chatData.speaker.scene = null; + if (!chatMessage.rolls.length && $(theatre.theatreChatCover).hasClass("theatre-control-chat-cover-ooc")) { + const user = game.users.get(chatMessage.user.id); + chatData.speaker.alias = user.name; chatData.type = CONST.CHAT_MESSAGE_TYPES.OOC; - chatMessage.data.update(chatData); + chatMessage.updateSource(chatData); return; } - if (!chatMessage.data.roll && Theatre.instance.speakingAs && Theatre.instance.usersTyping[chatMessage.data.user.id]) { - let theatreId = Theatre.instance.usersTyping[chatMessage.data.user.id].theatreId; + if (!chatMessage.rolls.length && Theatre.instance.speakingAs && Theatre.instance.usersTyping[chatMessage.user.id]) { + let theatreId = Theatre.instance.usersTyping[chatMessage.user.id].theatreId; let insert = Theatre.instance.getInsertById(theatreId); let actorId = theatreId.replace("theatre-", ""); let actor = game.actors.get(actorId) || null; if (Theatre.DEBUG) console.log("speakingAs %s", theatreId); - if (insert && chatMessage.data.speaker) { + if (insert && chatMessage.speaker) { let label = Theatre.instance._getLabelFromInsert(insert); let name = label.text; - let theatreColor = Theatre.instance.getPlayerFlashColor(chatMessage.data.user.id, insert.textColor); + let theatreColor = Theatre.instance.getPlayerFlashColor(chatMessage.user.id, insert.textColor); if (Theatre.DEBUG) console.log("name is %s", name); chatData.speaker.alias = name; - chatData.speaker.actor = null; - chatData.speaker.scene = null; //chatData.flags.theatreColor = theatreColor; chatData.type = CONST.CHAT_MESSAGE_TYPES.IC; // if delay emote is active @@ -267,10 +267,7 @@ Hooks.on("preCreateChatMessage", function (chatMessage) { let label = Theatre.instance._getLabelFromInsert(insert); let name = label.text; let theatreColor = Theatre.instance.getPlayerFlashColor(chatData.user, insert.textColor); - chatData.speaker = {}; chatData.speaker.alias = name; - chatData.speaker.actor = null; - chatData.speaker.scene = null; //chatData.flags.theatreColor = theatreColor; chatData.type = CONST.CHAT_MESSAGE_TYPES.IC; // if delay emote is active @@ -281,27 +278,29 @@ Hooks.on("preCreateChatMessage", function (chatMessage) { Theatre.instance.delayedSentState = 0; } } else if (Theatre.instance.speakingAs == Theatre.NARRATOR) { - chatData.speaker = {}; chatData.speaker.alias = game.i18n.localize("Theatre.UI.Chat.Narrator"); - chatData.speaker.actor = null; - chatData.speaker.scene = null; chatData.type = CONST.CHAT_MESSAGE_TYPES.IC; } + + if (!chatData.flags) chatData.flags = {}; + chatData.flags[Theatre.SETTINGS] = { theatreMessage: true }; } // alter message data - // append chat emote braces TODO make a setting - if (Theatre.DEBUG) console.log("speaker? ", chatMessage.data.speaker); + // append chat emote braces + if (Theatre.DEBUG) console.log("speaker? ", chatMessage.speaker); if ( Theatre.instance.isQuoteAuto && - !chatMessage.data.roll && - chatMessage.data.speaker && + !chatMessage.rolls.length && + chatMessage.speaker && (chatData.speaker.actor || chatData.speaker.token || chatData.speaker.alias) && - !chatMessage.data.content.match(/\[\s\S]*\<\/div\>/) + !chatMessage.content.match(/\[\s\S]*\<\/div\>/) ) { - chatData.content = game.i18n.localize("Theatre.Text.OpenBracket") + chatMessage.data.content + game.i18n.localize("Theatre.Text.CloseBracket"); + chatData.content = + game.i18n.localize(`Theatre.Text.OpenBracket.${Theatre.instance.settings.quoteType}`) + + chatMessage.content + + game.i18n.localize(`Theatre.Text.CloseBracket.${Theatre.instance.settings.quoteType}`); } - - chatMessage.data.update(chatData); + chatMessage.updateSource(chatData); }); /** @@ -320,11 +319,11 @@ Hooks.on("createChatMessage", function (chatEntity, _, userId) { } // slash commands are pass through - let chatData = chatEntity.data; + let chatData = chatEntity; if ( chatData.content.startsWith("<") || //Bandaid fix so that texts that start with html formatting don't utterly break it chatData.content.startsWith("/") || - chatData.roll || + chatData.rolls.length || chatData.emote || chatData.type == CONST.CHAT_MESSAGE_TYPES.OOC || //|| Object.keys(chatData.speaker).length == 0 @@ -474,6 +473,11 @@ Hooks.on("createChatMessage", function (chatEntity, _, userId) { } }); +Hooks.on("renderChatMessage", function (ChatMessage, html, data) { + if (Theatre.instance.settings.ignoreMessagesToChat && ChatMessage.flags?.[Theatre.SETTINGS]?.theatreMessage) html[0].style.display = "none"; + return true; +}); + Hooks.on("renderChatLog", function (app, html, data) { if (data.cssId === "chat-popout") return; theatre.initialize(); @@ -490,8 +494,7 @@ Hooks.on("getActorDirectoryEntryContext", async (html, options) => { if (!game.user.isGM && game.settings.get("theatre", "gmOnly")) return; const getActorData = (target) => { - const actor = game.actors.get(target.data("documentId")); - return actor.data; + return game.actors.get(target.data("documentId")); }; options.splice( @@ -516,11 +519,8 @@ Hooks.on("getActorDirectoryEntryContext", async (html, options) => { var theatre = null; Hooks.once("setup", () => { theatre = new Theatre(); -}); -Hooks.once("init", () => { // module keybinds - game.keybindings.register("theatre", "unfocusTextArea", { name: "Theatre.UI.Keybinds.unfocusTextArea", hint: "", @@ -551,7 +551,7 @@ Hooks.once("init", () => { onDown: () => { const ownedActors = game.actors.filter((a) => a.permission === 3); const ownedTokens = ownedActors.map((a) => a.getActiveTokens()); - for (const tokenArray of ownedTokens) tokenArray.forEach((t) => Theatre.addToNavBar(t.actor.data)); + for (const tokenArray of ownedTokens) tokenArray.forEach((t) => Theatre.addToNavBar(t.actor)); }, restricted: false, }); @@ -566,9 +566,19 @@ Hooks.once("init", () => { }, ], onDown: () => { - for (const tkn of canvas.tokens.controlled) Theatre.addToNavBar(tkn.actor.data); + for (const tkn of canvas.tokens.controlled) Theatre.addToNavBar(tkn.actor); }, - restricted: false, + restricted: true, + }); + + game.keybindings.register("theatre", `removeSelectedFromStage`, { + name: "Theatre.UI.Keybinds.removeSelectedFromStage", + hint: "", + editable: [], + onDown: (context) => { + for (const tkn of canvas.tokens.controlled) Theatre.removeFromNavBar(tkn.actor); + }, + restricted: true, }); game.keybindings.register("theatre", "narratorMode", { @@ -587,7 +597,7 @@ Hooks.once("init", () => { document.getElementById("chat-message").blur(); }, - restricted: false, + restricted: true, }); game.keybindings.register("theatre", "flipPortrait", { @@ -759,7 +769,7 @@ Hooks.once("init", () => { for (let i = 1; i < 11; i++) { game.keybindings.register("theatre", `activateStaged${i}`, { - name: `Theatre.UI.Keybinds.activateStaged${i}`, + name: game.i18n.format(`Theatre.UI.Keybinds.activateStaged`, { number: i }), hint: "", editable: [ { @@ -775,10 +785,11 @@ Hooks.once("init", () => { document.getElementById("chat-message").blur(); }, restricted: false, + reservedModifiers: ["Shift"], }); game.keybindings.register("theatre", `removeStaged${i}`, { - name: `Theatre.UI.Keybinds.removeStaged${i}`, + name: game.i18n.format(`Theatre.UI.Keybinds.removeStaged`, { number: i }), hint: "", editable: [ { @@ -791,7 +802,7 @@ Hooks.once("init", () => { const id = ids[i - 1]; if (id) Theatre.instance.removeInsertById(id); }, - restricted: false, + restricted: true, }); } }); diff --git a/app/lang/en.json b/app/lang/en.json index fa4b048..7646d4b 100644 --- a/app/lang/en.json +++ b/app/lang/en.json @@ -1,203 +1,225 @@ { - "I18N.MAINTAINERS" : ["PakkiSukibe"], + "I18N.MAINTAINERS": ["PakkiSukibe"], - "Header.Override.Token" : "Token", - "Header.Override.Sheet" : "Sheet", - "Header.Override.Import" : "Import", - "Header.Override.Close" : "Close", + "Header": { + "Override": { + "Token": "Token", + "Sheet": "Sheet", + "Import": "Import", + "Close": "Close" + } + }, - "Theatre.UI.Chat.Narrator" : "Narrator", - - "Theatre.UI.Title.EmoteSelector" : "Emote Selector", - "Theatre.UI.Title.SuppressTheatre" : "Suppress Theatre", - "Theatre.UI.Title.Narrator" : "Narrator Mode", - "Theatre.UI.Title.ResyncGM" : "Resync All Player Theatres", - "Theatre.UI.Title.ResyncPlayer" : "Resync Theatre to GM", - "Theatre.UI.Title.QuoteToggle" : "Automatic Alias Quotes", - "Theatre.UI.Title.DelayEmoteToggle" : "Delay Emote Until Message", - "Theatre.UI.Title.CinemaSelector" : "Cinematics", - "Theatre.UI.Title.AddToStage" : "Add To Staging Area", - "Theatre.UI.Title.ConfigureTheatre" : "Configure Theatre Settings For Actor", - "Theatre.UI.Title.ChooseEmoteIcon" : "Choose Emote Icon", - "Theatre.UI.Title.ChooseEmoteName" : "Change Custom Emote Name", - "Theatre.UI.Title.DeleteCustomEmote" : "Delete Custom Emote", - "Theatre.UI.Title.FontType" : "Font Type", - "Theatre.UI.Title.FontSize" : "Font Size", - "Theatre.UI.Title.FontColor" : "Font Color", - - "Theatre.UI.Notification.CannotMoveOwner" : "You must control the actor you wish to move", - "Theatre.UI.Notification.CannotMoveControlled" : "Cannot move to a non-player controlled actor", - "Theatre.UI.Notification.CannotSwapOwner" : "You must control one of the actors you wish to swap", - "Theatre.UI.Notification.CannotSwapControlled" : "Cannot swap with a non-player controlled actor", - "Theatre.UI.Notification.DoNotControl" : "You do not control this actor", - "Theatre.UI.Notification.CannotPushFront" : "You cannot push this actor to the front as that actor is not player controlled", - "Theatre.UI.Notification.CannotPushBack" : "You cannot push this actor to the back as that actor is not player controlled", - "Theatre.UI.Notification.ResyncPlayer" : "Resyncing theatre from a connected player: ", - "Theatre.UI.Notification.ResyncGM" : "Resyncing theatre with the GM", - "Theatre.UI.Notification.AlreadyStaged" : " is already staged", - "Theatre.UI.Notification.ImageLoadFail_P1" : "Image load has failed for '", - "Theatre.UI.Notification.ImageLoadFail_P2" : "' with path '", - "Theatre.UI.Notification.TooLongDecayMin" : "Text decay minimum is too long, setting it to the maximum value 600s", - "Theatre.UI.Notification.TooLongDecayRate" : "Text decay rate is too long, setting it to the maximum value 10s", - "Theatre.UI.Notification.InvalidDecayMin" : "Text decay minimum is invalid, setting it to the default of 30s", - "Theatre.UI.Notification.InvalidDecayRate" : "Text decay rate is invalid, setting it to the default of 1s", - "Theatre.UI.Notification.BadCustomEmote" : "Bad custom emote name (must be defined), not submitting Theatre configuration changes", - "Theatre.UI.Notification.BadFilepath" : "Bad File Path exists in the submission, rejecting Theatre configuration changes : ", - - "Theatre.UI.Notification.ErrorFatal" : "Fatal Error, please submit console log (f12 -> console) with bug report", - - "Theatre.UI.Settings.displayMode" : "Theatre Bar Display Mode", - "Theatre.UI.Settings.displayModeHint" : "The display mode for the text area under a theatre insert. Text Box style is geared for text-based games as it provides a solid background for the text. Light Box style is geared for voice or voice hybrid games with a visual novel look and feel. Clear style is intended for voice only games where text isn't as important since the text *will be difficult to read*; it is more intended as a mode for puppeting the portrait by movements and emotes alone.", - "Theatre.UI.Settings.displayModeTextBox" : "Text Box Style", - "Theatre.UI.Settings.displayModeLightBox" : "Light Box Style", - "Theatre.UI.Settings.displayModeClearBox" : "Clear Box Style", - "Theatre.UI.Settings.gmOnly" : "GM controls only", - "Theatre.UI.Settings.gmOnlyHint" : "If enabled, only the GM will be able to control the stage. The Theatre controls will be hidden for the players.", - "Theatre.UI.Settings.narrHeight" : "Narrator Bar Position", - "Theatre.UI.Settings.narrHeightHint" : "The position of the narrator bar as a percentage of the screen height.", - "Theatre.UI.Settings.textDecayMin" : "Minimum Text Decay Time", - "Theatre.UI.Settings.textDecayMinHint" : "The minimum amount of time in seconds before a theatre text entry will decay.", - "Theatre.UI.Settings.textDecayRate" : "Text Decay Rate", - "Theatre.UI.Settings.textDecayRateHint" : "The rate at which text will decay, based on the length of the message in seconds. This is applied *per character*, thus a 100 character message is 100s before decay if the decay rate is 1s, OR the minimum decay time, whichever is greater.", - "Theatre.UI.Settings.nameFont": "Actor Name Font", - "Theatre.UI.Settings.nameFontHint": "Put in the name of the font you want to use. If the font exists in Theatre, it can be used. Requires actors to re-stage or for the GM to resync.", - "Theatre.UI.Settings.nameFontSize": "Actor Name Size (Experimental)", - "Theatre.UI.Settings.nameFontSizeHint": "Sets the size of the name font. Note that the sizes may be different depending on your display or font choice. Using huge sizes is not recommended.", - "Theatre.UI.Settings.autoHideBottom": "Auto Hide Bottom", - "Theatre.UI.Settings.autoHideBottomHint": "Hide bottom UI(player&hotbar) when actor shows on stage.", - "Theatre.UI.Settings.suppressMacroHotbar": "Show Player List and Macro Hotbar When Stage is Suppressed", - "Theatre.UI.Settings.removeLabelSheetHeader": "Remove label from the header character sheet", - "Theatre.UI.Settings.removeLabelSheetHeaderHint": "Remove label from the header character sheet, Useful for little screen and mobile", - - "Theatre.UI.Keybinds.unfocusTextArea": "Unfocus Text Area", - "Theatre.UI.Keybinds.addOwnedToStage": "Add Owned Actors to Stage", - "Theatre.UI.Keybinds.addSelectedToStage": "Add Selected Tokens to Stage", - "Theatre.UI.Keybinds.narratorMode": "Activate Narrator Mode", - "Theatre.UI.Keybinds.flipPortrait": "Flip Portrait", - "Theatre.UI.Keybinds.nudgePortraitLeft": "Nudge Portrait Left", - "Theatre.UI.Keybinds.nudgePortraitRight": "Nudge Portrait Right", - "Theatre.UI.Keybinds.nudgePortraitUp": "Nudge Portrait Up", - "Theatre.UI.Keybinds.nudgePortraitDown": "Nudge Portrait Down", - "Theatre.UI.Keybinds.activateStaged1": "Activate Staged Actor Number 1", - "Theatre.UI.Keybinds.activateStaged2": "Activate Staged Actor Number 2", - "Theatre.UI.Keybinds.activateStaged3": "Activate Staged Actor Number 3", - "Theatre.UI.Keybinds.activateStaged4": "Activate Staged Actor Number 4", - "Theatre.UI.Keybinds.activateStaged5": "Activate Staged Actor Number 5", - "Theatre.UI.Keybinds.activateStaged6": "Activate Staged Actor Number 6", - "Theatre.UI.Keybinds.activateStaged7": "Activate Staged Actor Number 7", - "Theatre.UI.Keybinds.activateStaged8": "Activate Staged Actor Number 8", - "Theatre.UI.Keybinds.activateStaged9": "Activate Staged Actor Number 9", - "Theatre.UI.Keybinds.activateStaged10": "Activate Staged Actor Number 10", - "Theatre.UI.Keybinds.removeStaged1": "Remove Staged Actor Number 1", - "Theatre.UI.Keybinds.removeStaged2": "Remove Staged Actor Number 2", - "Theatre.UI.Keybinds.removeStaged3": "Remove Staged Actor Number 3", - "Theatre.UI.Keybinds.removeStaged4": "Remove Staged Actor Number 4", - "Theatre.UI.Keybinds.removeStaged5": "Remove Staged Actor Number 5", - "Theatre.UI.Keybinds.removeStaged6": "Remove Staged Actor Number 6", - "Theatre.UI.Keybinds.removeStaged7": "Remove Staged Actor Number 7", - "Theatre.UI.Keybinds.removeStaged8": "Remove Staged Actor Number 8", - "Theatre.UI.Keybinds.removeStaged9": "Remove Staged Actor Number 9", - "Theatre.UI.Keybinds.removeStaged10": "Remove Staged Actor Number 10", - - "Theatre.MOTD.Header" : "Theatre Notification", - "Theatre.MOTD.OldVersion" : "Theatre is currently out of date, please have the GM update theatre in the setup screen.", - - "Theatre.UI.Config.Stage" : "Stage", - "Theatre.UI.Config.AddToStage" : "Add to Stage", - "Theatre.UI.Config.RemoveFromStage" : "Remove from Stage", - "Theatre.UI.Config.Theatre" : "Theatre", - "Theatre.UI.Config.ConfigureTheatre" : "Configure Theatre", - "Theatre.UI.Config.Main" : "Main", - "Theatre.UI.Config.AddEmote" : "Add Emote", - "Theatre.UI.Config.ConfigureEmotes" : "Configure Emotes", - "Theatre.UI.Config.ConfigureEmote" : "Configure Emote", - "Theatre.UI.Config.ConfigureEmotesHint" : "Set emote images for the default set, or add custom emotes.", - "Theatre.UI.Config.InsertName" : "Theatre Insert Name/Label", - "Theatre.UI.Config.SetTopAlign" : "Set the Top Alignment", - "Theatre.UI.Config.SetTopAlignTop" : "Top of Dialog Box", - "Theatre.UI.Config.SetTopAlignBottom" : "Bottom of Dialog Box", - "Theatre.UI.Config.SetDefaultInsert" : "Set the Default Theatre Insert", - "Theatre.UI.Config.BaseInsert" : "Base Theatre Insert", - "Theatre.UI.Config.SaveSettings" : "Save Settings", - "Theatre.UI.Config.PathPlaceholder" : "path/image.png", - "Theatre.UI.Config.CustomEmotePlaceholder" : "Custom Name", - "Theatre.UI.Config.DisableDefaultAnim" : "Disable Default Animations", - "Theatre.UI.Config.DisableDefaultAnimHint" : "Disables all default animations for emotes, this includes the bubble and any other animation that comes as stock.", - - "Theatre.Text.OpenBracket" : "\"", - "Theatre.Text.CloseBracket" : "\"", - "Theatre.Text.FontSizeSmall" : "Small", - "Theatre.Text.FontSizeNormal" : "Normal", - "Theatre.Text.FontSizeLarge" : "Large", - - "Theatre.Emote.Label" : "Emotes", - "Theatre.Emote.Happy" : "Happy", - "Theatre.Emote.Smile" : "Smile", - "Theatre.Emote.Grin" : "Grin", - "Theatre.Emote.HappyTears" : "Happy to Tears", - "Theatre.Emote.Sad" : "Sad", - "Theatre.Emote.Frown" : "Frown", - "Theatre.Emote.Cry" : "Crying", - "Theatre.Emote.Serious" : "Serious", - "Theatre.Emote.Annoyed" : "Annoyed", - "Theatre.Emote.Frustrated" : "Frustrated", - "Theatre.Emote.Angry" : "Angry", - "Theatre.Emote.Laughing" : "Laughing", - "Theatre.Emote.LaughingSquint" : "Laughing Squint", - "Theatre.Emote.ROFL" : "Laughing Roll", - "Theatre.Emote.Worried" : "Worried", - "Theatre.Emote.Meh" : "Meh", - "Theatre.Emote.Surprised" : "Surprised", - "Theatre.Emote.Wink" : "Wink", - "Theatre.Emote.Tongue" : "Tongue", - "Theatre.Emote.Blushing" : "Blushing", - "Theatre.Emote.Hearts" : "Hearts", - "Theatre.Emote.Kiss" : "Blow Kiss", - "Theatre.Emote.Sleeping" : "Sleeping", - "Theatre.Emote.Thinking" : "Thinking", - "Theatre.Emote.Smug" : "Smug", - "Theatre.Emote.Playful" : "Playful", - "Theatre.Emote.Dissatisfied" : "Dissatisfied", - "Theatre.Emote.Panic" : "Panic", - "Theatre.Emote.Dizzy" : "Dizzy", - "Theatre.Emote.Idea" : "Idea", - "Theatre.Emote.Confused" : "Confused", - "Theatre.Emote.Speechless" : "Speechless", - "Theatre.Emote.Awe-Struck" : "Awe-Struck", - "Theatre.Emote.Mischevious" : "Mischevious", - "Theatre.Emote.Innocent" : "Innocent", - "Theatre.Emote.CareFree" : "Care Free", - "Theatre.Emote.Scared" : "Scared", - "Theatre.Emote.Pleased" : "Pleased", - "Theatre.Emote.Lazy" : "Lazy", - "Theatre.Emote.Ambitious" : "Ambitious", - "Theatre.Emote.Correct" : "Correct", - "Theatre.Emote.Wrong" : "Wrong", - - "Theatre.Flyin.Label" : "Fly-In", - "Theatre.Flyin.Typewriter" : "Typewriter", - "Theatre.Flyin.Fadein" : "Fade-In", - "Theatre.Flyin.Slidein" : "Slide-In", - "Theatre.Flyin.Scalein" : "Scale-In", - "Theatre.Flyin.Fallin" : "Fall-in", - "Theatre.Flyin.Spin" : "Spin", - "Theatre.Flyin.SpinScale" : "SpinScale", - "Theatre.Flyin.Outlaw" : "Outlaw", - "Theatre.Flyin.Vortex" : "Vortex", - "Theatre.Flyin.Assemble" : "Assemble", - - "Theatre.Standing.Label" : "Standing", - "Theatre.Standing.Spooky" : "Spooky", - "Theatre.Standing.Insane" : "Insane", - "Theatre.Standing.Excited" : "Excited", - "Theatre.Standing.Bubbly" : "Bubbly", - "Theatre.Standing.Violent" : "Violent", - "Theatre.Standing.Impact" : "Impact", - "Theatre.Standing.Quiver" : "Quiver", - "Theatre.Standing.Wave" : "Wave", - "Theatre.Standing.Fade" : "Fade", - "Theatre.Standing.None" : "None", - - "Theatre.Other" : "Other", - "Theatre.NotYet" : "Not yet implemented" + "Theatre": { + "UI": { + "Chat": { "Narrator": "Narrator" }, + "Title": { + "EmoteSelector": "Emote Selector", + "SuppressTheatre": "Suppress Theatre", + "Narrator": "Narrator Mode", + "ResyncGM": "Resync All Player Theatres", + "ResyncPlayer": "Resync Theatre to GM", + "QuoteToggle": "Automatic Alias Quotes", + "DelayEmoteToggle": "Delay Emote Until Message", + "CinemaSelector": "Cinematics", + "AddToStage": "Add To Staging Area", + "ConfigureTheatre": "Configure Theatre Settings For Actor", + "ChooseEmoteIcon": "Choose Emote Icon", + "ChooseEmoteName": "Change Custom Emote Name", + "DeleteCustomEmote": "Delete Custom Emote", + "FontType": "Font Type", + "FontSize": "Font Size", + "FontColor": "Font Color" + }, + "Notification": { + "CannotMoveOwner": "You must control the actor you wish to move", + "CannotMoveControlled": "Cannot move to a non-player controlled actor", + "CannotSwapOwner": "You must control one of the actors you wish to swap", + "CannotSwapControlled": "Cannot swap with a non-player controlled actor", + "DoNotControl": "You do not control this actor", + "CannotPushFront": "You cannot push this actor to the front as that actor is not player controlled", + "CannotPushBack": "You cannot push this actor to the back as that actor is not player controlled", + "ResyncPlayer": "Resyncing theatre from a connected player: ", + "ResyncGM": "Resyncing theatre with the GM", + "AlreadyStaged": " is already staged", + "ImageLoadFail_P1": "Image load has failed for '", + "ImageLoadFail_P2": "' with path '", + "TooLongDecayMin": "Text decay minimum is too long, setting it to the maximum value 600s", + "TooLongDecayRate": "Text decay rate is too long, setting it to the maximum value 10s", + "InvalidDecayMin": "Text decay minimum is invalid, setting it to the default of 30s", + "InvalidDecayRate": "Text decay rate is invalid, setting it to the default of 1s", + "BadCustomEmote": "Bad custom emote name (must be defined), not submitting Theatre configuration changes", + "BadFilepath": "Bad File Path exists in the submission, rejecting Theatre configuration changes : ", + "ErrorFatal": "Fatal Error, please submit console log (f12 -> console) with bug report" + }, + "Settings": { + "displayMode": "Theatre Bar Display Mode", + "displayModeHint": "The display mode for the text area under a theatre insert. Text Box style is geared for text-based games as it provides a solid background for the text. Light Box style is geared for voice or voice hybrid games with a visual novel look and feel. Clear style is intended for voice only games where text isn't as important since the text *will be difficult to read*; it is more intended as a mode for puppeting the portrait by movements and emotes alone.", + "displayModeTextBox": "Text Box Style", + "displayModeLightBox": "Light Box Style", + "displayModeClearBox": "Clear Box Style", + "gmOnly": "GM controls only", + "gmOnlyHint": "If enabled, only the GM will be able to control the stage. The Theatre controls will be hidden for the players.", + "narrHeight": "Narrator Bar Position", + "narrHeightHint": "The position of the narrator bar as a percentage of the screen height.", + "textDecayMin": "Minimum Text Decay Time", + "textDecayMinHint": "The minimum amount of time in seconds before a theatre text entry will decay.", + "textDecayRate": "Text Decay Rate", + "textDecayRateHint": "The rate at which text will decay, based on the length of the message in seconds. This is applied *per character*, thus a 100 character message is 100s before decay if the decay rate is 1s, OR the minimum decay time, whichever is greater.", + "nameFont": "Actor Name Font", + "nameFontHint": "Put in the name of the font you want to use. If the font exists in Theatre, it can be used. Requires actors to re-stage or for the GM to resync.", + "nameFontSize": "Actor Name Size (Experimental)", + "nameFontSizeHint": "Sets the size of the name font. Note that the sizes may be different depending on your display or font choice. Using huge sizes is not recommended.", + "autoHideBottom": "Auto Hide Bottom", + "autoHideBottomHint": "Hide bottom UI(player&hotbar) when actor shows on stage.", + "suppressMacroHotbar": "Show Player List and Macro Hotbar When Stage is Suppressed", + "removeLabelSheetHeader": "Remove label from the header character sheet", + "removeLabelSheetHeaderHint": "Remove label from the header character sheet, Useful for little screen and mobile", + "ignoreMessagesToChat": "Ignore Theatre Messages From Chat", + "ignoreMessagesToChatHint": "Ignores messages sent during Theatre Mode from chat. Disabling this message will make them appear again.", + "quoteType": "Quote Type", + "quoteTypeHint": "When using the {setting} option, the chosen pattern of quotes will be used.", + "quoteTypeChoices": { + "0": "'Single Quote'", + "1": "\"Double Quotes\"", + "2": "【Fāngtóu Kuòhào】", + "3": "「Kagikakko」", + "4": "『Nijū Kagiyamakakko』" + } + }, + "Keybinds": { + "unfocusTextArea": "Unfocus Text Area", + "addOwnedToStage": "Add Owned Actors to Stage", + "addSelectedToStage": "Add Selected Tokens to Stage", + "removeSelectedFromStage": "Remove Selected Tokens from Stage", + "narratorMode": "Activate Narrator Mode", + "flipPortrait": "Flip Portrait", + "nudgePortraitLeft": "Nudge Portrait Left", + "nudgePortraitRight": "Nudge Portrait Right", + "nudgePortraitUp": "Nudge Portrait Up", + "nudgePortraitDown": "Nudge Portrait Down", + "activateStaged": "Activate Staged Actor Number {number}", + "removeStaged": "Remove Staged Actor Number {number}" + }, + "MOTD": { + "Header": "Theatre Notification", + "OldVersion": "Theatre is currently out of date, please have the GM update theatre in the setup screen." + }, + "Config": { + "Stage": "Stage", + "AddToStage": "Add to Stage", + "RemoveFromStage": "Remove from Stage", + "Theatre": "Theatre", + "ConfigureTheatre": "Configure Theatre", + "Main": "Main", + "AddEmote": "Add Emote", + "ConfigureEmotes": "Configure Emotes", + "ConfigureEmote": "Configure Emote", + "ConfigureEmotesHint": "Set emote images for the default set, or add custom emotes.", + "InsertName": "Theatre Insert Name/Label", + "SetTopAlign": "Set the Top Alignment", + "SetTopAlignTop": "Top of Dialog Box", + "SetTopAlignBottom": "Bottom of Dialog Box", + "SetDefaultInsert": "Set the Default Theatre Insert", + "BaseInsert": "Base Theatre Insert", + "SaveSettings": "Save Settings", + "PathPlaceholder": "path/image.png", + "CustomEmotePlaceholder": "Custom Name", + "DisableDefaultAnim": "Disable Default Animations", + "DisableDefaultAnimHint": "Disables all default animations for emotes, this includes the bubble and any other animation that comes as stock." + } + }, + "Text": { + "OpenBracket": { + "0": "'", + "1": "\"", + "2": "【", + "3": "「", + "4": "『" + }, + "CloseBracket": { + "0": "'", + "1": "\"", + "2": "】", + "3": "」", + "4": "』" + }, + "FontSizeSmall": "Small", + "FontSizeNormal": "Normal", + "FontSizeLarge": "Large" + }, + "Emote": { + "Label": "Emotes", + "Happy": "Happy", + "Smile": "Smile", + "Grin": "Grin", + "HappyTears": "Happy to Tears", + "Sad": "Sad", + "Frown": "Frown", + "Cry": "Crying", + "Serious": "Serious", + "Annoyed": "Annoyed", + "Frustrated": "Frustrated", + "Angry": "Angry", + "Laughing": "Laughing", + "LaughingSquint": "Laughing Squint", + "ROFL": "Laughing Roll", + "Worried": "Worried", + "Meh": "Meh", + "Surprised": "Surprised", + "Wink": "Wink", + "Tongue": "Tongue", + "Blushing": "Blushing", + "Hearts": "Hearts", + "Kiss": "Blow Kiss", + "Sleeping": "Sleeping", + "Thinking": "Thinking", + "Smug": "Smug", + "Playful": "Playful", + "Dissatisfied": "Dissatisfied", + "Panic": "Panic", + "Dizzy": "Dizzy", + "Idea": "Idea", + "Confused": "Confused", + "Speechless": "Speechless", + "Awe-Struck": "Awe-Struck", + "Mischevious": "Mischevious", + "Innocent": "Innocent", + "CareFree": "Care Free", + "Scared": "Scared", + "Pleased": "Pleased", + "Lazy": "Lazy", + "Ambitious": "Ambitious", + "Correct": "Correct", + "Wrong": "Wrong" + }, + "Flyin": { + "Label": "Fly-In", + "Typewriter": "Typewriter", + "Fadein": "Fade-In", + "Slidein": "Slide-In", + "Scalein": "Scale-In", + "Fallin": "Fall-in", + "Spin": "Spin", + "SpinScale": "SpinScale", + "Outlaw": "Outlaw", + "Vortex": "Vortex", + "Assemble": "Assemble" + }, + "Standing": { + "Label": "Standing", + "Spooky": "Spooky", + "Insane": "Insane", + "Excited": "Excited", + "Bubbly": "Bubbly", + "Violent": "Violent", + "Impact": "Impact", + "Quiver": "Quiver", + "Wave": "Wave", + "Fade": "Fade", + "None": "None" + }, + "Other": "Other", + "NotYet": "Not yet implemented" + } } diff --git a/app/packs/theatre-inserts-macros.db b/app/packs/theatre-inserts-macros.db index 4850cc4..744890d 100644 --- a/app/packs/theatre-inserts-macros.db +++ b/app/packs/theatre-inserts-macros.db @@ -1,2 +1,2 @@ -{"name":"Add Owned Tokens to Stage","type":"script","author":"2eCcEi9HdTwCxqFx","img":"icons/svg/dice-target.svg","scope":"global","command":"const ownedActors = game.actors.filter(a => a.permission === 3);\nconst ownedTokens = ownedActors.map(a => a.getActiveTokens());\n\nfor (const tokenArray of ownedTokens) {\n tokenArray.forEach(t => Theatre.addToNavBar(t.actor.data));\n}","folder":null,"sort":0,"permission":{"default":0,"2eCcEi9HdTwCxqFx":3},"flags":{"core":{"sourceId":"Macro.bnLRubdIw6rmj4CB"}},"_id":"O4bIjZLeC6KYwdj2"} -{"name":"Add Selected Tokens to Stage","type":"script","author":"2eCcEi9HdTwCxqFx","img":"icons/svg/dice-target.svg","scope":"global","command":"for (const tkn of canvas.tokens.controlled) {\n Theatre.addToNavBar(tkn.actor.data);\n}","folder":null,"sort":0,"permission":{"default":0,"2eCcEi9HdTwCxqFx":3},"flags":{"core":{"sourceId":"Macro.ue9fFNkWIxT3Y5hK"}},"_id":"SiNOxyDFzz7V1ptf"} +{"name":"Add Owned Tokens to Stage","type":"script","author":"2eCcEi9HdTwCxqFx","img":"icons/svg/dice-target.svg","scope":"global","command":"const ownedActors = game.actors.filter(a => a.permission === 3);\nconst ownedTokens = ownedActors.map(a => a.getActiveTokens());\n\nfor (const tokenArray of ownedTokens) {\n tokenArray.forEach(t => Theatre.addToNavBar(t.actor));\n}","folder":null,"sort":0,"permission":{"default":0,"2eCcEi9HdTwCxqFx":3},"flags":{"core":{"sourceId":"Macro.bnLRubdIw6rmj4CB"}},"_id":"O4bIjZLeC6KYwdj2"} +{"name":"Add Selected Tokens to Stage","type":"script","author":"2eCcEi9HdTwCxqFx","img":"icons/svg/dice-target.svg","scope":"global","command":"for (const tkn of canvas.tokens.controlled) {\n Theatre.addToNavBar(tkn.actor);\n}","folder":null,"sort":0,"permission":{"default":0,"2eCcEi9HdTwCxqFx":3},"flags":{"core":{"sourceId":"Macro.ue9fFNkWIxT3Y5hK"}},"_id":"SiNOxyDFzz7V1ptf"}