From bfd3f557e4d8e237a0b8fb8ca50f7ca1e0fa27f8 Mon Sep 17 00:00:00 2001 From: Lucy Date: Wed, 18 Dec 2024 21:08:52 -0500 Subject: [PATCH] 516: fix chat window z-fighting and tgui-say escape key Port of https://github.com/ParadiseSS13/Paradise/pull/27676, which in turn is a port of https://github.com/VOREStation/VOREStation/pull/16713 and https://github.com/VOREStation/VOREStation/pull/16734 --- code/modules/tgui_panel/external.dm | 9 +- interface/skin.dmf | 42 +- tgui/global.d.ts | 5 + tgui/packages/common/keys.ts | 18 +- tgui/packages/tgui-panel/chat/renderer.jsx | 4 +- tgui/packages/tgui-panel/index.jsx | 10 +- tgui/packages/tgui-say/TguiSay.tsx | 9 +- .../tgui/interfaces/KeyComboModal.tsx | 8 +- tgui/public/tgui.html | 1315 +++++++++-------- 9 files changed, 760 insertions(+), 660 deletions(-) diff --git a/code/modules/tgui_panel/external.dm b/code/modules/tgui_panel/external.dm index 692244a6e80d..c7dfa0ae8f7a 100644 --- a/code/modules/tgui_panel/external.dm +++ b/code/modules/tgui_panel/external.dm @@ -19,22 +19,19 @@ // Failed to fix, using tgalert as fallback action = tgalert(src, "Did that work?", "", "Yes", "No, switch to old ui") if (action == "No, switch to old ui") - winset(src, "output", "on-show=&is-disabled=0&is-visible=1") - winset(src, "browseroutput", "is-disabled=1;is-visible=0") + winset(src, "legacy_output_selector", "left=output_legacy") log_tgui(src, "Failed to fix.", context = "verb/fix_tgui_panel") /client/proc/nuke_chat() // Catch all solution (kick the whole thing in the pants) - winset(src, "output", "on-show=&is-disabled=0&is-visible=1") - winset(src, "browseroutput", "is-disabled=1;is-visible=0") + winset(src, "legacy_output_selector", "left=output_legacy") if(!tgui_panel || !istype(tgui_panel)) log_tgui(src, "tgui_panel datum is missing", context = "verb/fix_tgui_panel") tgui_panel = new(src) tgui_panel.initialize(force = TRUE) // Force show the panel to see if there are any errors - winset(src, "output", "is-disabled=1&is-visible=0") - winset(src, "browseroutput", "is-disabled=0;is-visible=1") + winset(src, "legacy_output_selector", "left=output_browser") if(byond_version >= 516) var/list/options = list("byondstorage", "find") if(check_rights_for(src, R_DEBUG)) diff --git a/interface/skin.dmf b/interface/skin.dmf index 9a4704e95120..d46f5c55b184 100644 --- a/interface/skin.dmf +++ b/interface/skin.dmf @@ -226,7 +226,7 @@ window "infowindow" window "outputwindow" elem "outputwindow" type = MAIN - pos = 281,0 + pos = 0,0 size = 640x480 anchor1 = -1,-1 anchor2 = -1,-1 @@ -285,15 +285,26 @@ window "outputwindow" anchor2 = -1,-1 is-visible = false saved-params = "" - elem "browseroutput" - type = BROWSER + elem "legacy_output_selector" + type = CHILD pos = 0,0 size = 640x456 anchor1 = 0,0 anchor2 = 100,100 - is-visible = false - is-disabled = true - saved-params = "" + saved-params = "splitter" + left = "output_legacy" + is-vert = false + +window "output_legacy" + elem "output_legacy" + type = MAIN + pos = 0,0 + size = 640x456 + anchor1 = -1,-1 + anchor2 = -1,-1 + background-color = none + saved-params = "pos;size;is-minimized;is-maximized" + is-pane = true elem "output" type = OUTPUT pos = 0,0 @@ -301,6 +312,25 @@ window "outputwindow" anchor1 = 0,0 anchor2 = 100,100 is-default = true + saved-params = "max-lines" + +window "output_browser" + elem "output_browser" + type = MAIN + pos = 0,0 + size = 640x456 + anchor1 = -1,-1 + anchor2 = -1,-1 + background-color = none + saved-params = "pos;size;is-minimized;is-maximized" + is-pane = true + elem "browseroutput" + type = BROWSER + pos = 0,0 + size = 640x456 + anchor1 = 0,0 + anchor2 = 100,100 + background-color = none saved-params = "" window "popupwindow" diff --git a/tgui/global.d.ts b/tgui/global.d.ts index b1697d5fcdbc..b8b9a052b811 100644 --- a/tgui/global.d.ts +++ b/tgui/global.d.ts @@ -162,6 +162,11 @@ type ByondType = { */ parseJson(text: string): any; + /** + * Downloads a blob, platform-agnostic + */ + saveBlob(blob: Blob, filename: string, ext: string): void; + /** * Sends a message to `/datum/tgui_window` which hosts this window instance. */ diff --git a/tgui/packages/common/keys.ts b/tgui/packages/common/keys.ts index 61b79992b486..abbd6b49bb70 100644 --- a/tgui/packages/common/keys.ts +++ b/tgui/packages/common/keys.ts @@ -25,7 +25,8 @@ export enum KEY { Down = 'Down', End = 'End', Enter = 'Enter', - Escape = 'Esc', + Esc = 'Esc', + Escape = 'Escape', Home = 'Home', Insert = 'Insert', Left = 'Left', @@ -37,3 +38,18 @@ export enum KEY { Tab = 'Tab', Up = 'Up', } + +/** + * ### isEscape + * + * Checks if the user has hit the 'ESC' key on their keyboard. + * There's a weirdness in BYOND where this could be either the string + * 'Escape' or 'Esc' depending on the browser. This function handles + * both cases. + * + * @param key - the key to check, typically from event.key + * @returns true if key is Escape or Esc, false otherwise + */ +export const isEscape = (key: string): boolean => { + return key === KEY.Esc || key === KEY.Escape; +}; diff --git a/tgui/packages/tgui-panel/chat/renderer.jsx b/tgui/packages/tgui-panel/chat/renderer.jsx index fa04d94f38c6..31fe73dd4025 100644 --- a/tgui/packages/tgui-panel/chat/renderer.jsx +++ b/tgui/packages/tgui-panel/chat/renderer.jsx @@ -612,13 +612,13 @@ class ChatRenderer { + '\n' + '\n'; // Create and send a nice blob - const blob = new Blob([pageHtml]); + const blob = new Blob([pageHtml], { type: 'text/plain' }); const timestamp = new Date() .toISOString() .substring(0, 19) .replace(/[-:]/g, '') .replace('T', '-'); - window.navigator.msSaveBlob(blob, `ss13-chatlog-${timestamp}.html`); + Byond.saveBlob(blob, `ss13-chatlog-${timestamp}.html`, '.html'); } } diff --git a/tgui/packages/tgui-panel/index.jsx b/tgui/packages/tgui-panel/index.jsx index 95559291ee2d..9f43a3091e25 100644 --- a/tgui/packages/tgui-panel/index.jsx +++ b/tgui/packages/tgui-panel/index.jsx @@ -78,14 +78,8 @@ const setupApp = () => { Byond.subscribe((type, payload) => store.dispatch({ type, payload })); // Unhide the panel - Byond.winset('output', { - 'is-visible': false, - }); - Byond.winset('browseroutput', { - 'is-visible': true, - 'is-disabled': false, - pos: '0x0', - size: '0x0', + Byond.winset('legacy_output_selector', { + left: 'output_browser', }); // Resize the panel to match the non-browser output diff --git a/tgui/packages/tgui-say/TguiSay.tsx b/tgui/packages/tgui-say/TguiSay.tsx index 0a1c9c7e4efa..aee0d12a5cf5 100644 --- a/tgui/packages/tgui-say/TguiSay.tsx +++ b/tgui/packages/tgui-say/TguiSay.tsx @@ -6,7 +6,7 @@ import { byondMessages } from './timers'; import { dragStartHandler } from 'tgui/drag'; import { windowOpen, windowClose, windowSet } from './helpers'; import { BooleanLike } from 'common/react'; -import { KEY } from 'common/keys'; +import { isEscape, KEY } from 'common/keys'; type ByondOpen = { channel: Channel; @@ -252,9 +252,10 @@ export class TguiSay extends Component<{}, State> { this.handleIncrementChannel(); break; - case KEY.Escape: - this.handleClose(); - break; + default: + if (isEscape(event.key)) { + this.handleClose(); + } } } diff --git a/tgui/packages/tgui/interfaces/KeyComboModal.tsx b/tgui/packages/tgui/interfaces/KeyComboModal.tsx index 6d618fe01214..515f7162fb3f 100644 --- a/tgui/packages/tgui/interfaces/KeyComboModal.tsx +++ b/tgui/packages/tgui/interfaces/KeyComboModal.tsx @@ -1,4 +1,4 @@ -import { KEY } from 'common/keys'; +import { KEY, isEscape } from 'common/keys'; import { useBackend, useLocalState } from '../backend'; import { Autofocus, Box, Button, Section, Stack } from '../components'; import { Window } from '../layouts'; @@ -18,7 +18,7 @@ const isStandardKey = (event: KeyboardEvent): boolean => { event.key !== KEY.Alt && event.key !== KEY.Control && event.key !== KEY.Shift && - event.key !== KEY.Escape + !isEscape(event.key) ); }; @@ -93,7 +93,7 @@ export const KeyComboModal = (props) => { if (event.key === KEY.Enter) { act('submit', { entry: input }); } - if (event.key === KEY.Escape) { + if (isEscape(event.key)) { act('cancel'); } return; @@ -105,7 +105,7 @@ export const KeyComboModal = (props) => { setValue(formatKeyboardEvent(event)); setBinding(false); return; - } else if (event.key === KEY.Escape) { + } else if (isEscape(event.key)) { setValue(init_value); setBinding(false); return; diff --git a/tgui/public/tgui.html b/tgui/public/tgui.html index 7dded63eee27..8937a9443bc4 100644 --- a/tgui/public/tgui.html +++ b/tgui/public/tgui.html @@ -1,673 +1,730 @@ + - - - - - - - - - + + - - + + + + - - - - - - - - -
- - -
- - - A fatal exception has occurred at 002B:C562F1B7 in TGUI. The current - application will be terminated. Please remain calm. Get to the nearest - NTNet workstation and send the copy of the following stack trace to: - https://github.com/Monkestation/Monkestation2.0/. Thank you for your cooperation. - -
- -
- -