mirror of
https://github.com/CHOMPStation2/CHOMPStation2.git
synced 2026-01-02 05:23:31 +00:00
[MIRROR] tgui cleanup again (#11432)
Co-authored-by: Kashargul <144968721+Kashargul@users.noreply.github.com>
This commit is contained in:
committed by
GitHub
parent
77a99a4531
commit
15cbe5bee3
@@ -56,8 +56,7 @@
|
||||
"suspicious": {
|
||||
"noArrayIndexKey": "off",
|
||||
"noExplicitAny": "off",
|
||||
"noImplicitAnyLet": "off",
|
||||
"noAssignInExpressions": "warn"
|
||||
"noImplicitAnyLet": "off"
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
@@ -66,6 +66,12 @@
|
||||
/datum/preference/toggle/tgui_say_light/apply_to_client(client/client, value)
|
||||
client.tgui_say?.load()
|
||||
|
||||
/datum/preference/toggle/tgui_use_spellcheck
|
||||
category = PREFERENCE_CATEGORY_GAME_PREFERENCES
|
||||
savefile_key = "TGUI_ENABLE_SPELLCHECK"
|
||||
default_value = TRUE
|
||||
savefile_identifier = PREFERENCE_PLAYER
|
||||
|
||||
/datum/preference/toggle/tgui_say_emotes
|
||||
category = PREFERENCE_CATEGORY_GAME_PREFERENCES
|
||||
savefile_key = "tgui_say_emotes"
|
||||
|
||||
@@ -72,10 +72,11 @@
|
||||
|
||||
window.send_message("props", list(
|
||||
"lightMode" = client?.prefs?.read_preference(/datum/preference/toggle/tgui_say_light),
|
||||
"scale" = client.prefs?.read_preference(/datum/preference/toggle/ui_scale),
|
||||
"scale" = client?.prefs?.read_preference(/datum/preference/toggle/ui_scale),
|
||||
"minimumWidth" = minimum_width,
|
||||
"minimumHeight" = minimum_height,
|
||||
"maxLength" = max_length,
|
||||
"spellcheck" = client?.prefs?.read_preference(/datum/preference/toggle/tgui_use_spellcheck)
|
||||
))
|
||||
|
||||
stop_thinking()
|
||||
|
||||
@@ -126,6 +126,7 @@
|
||||
data["placeholder"] = default // Default is a reserved keyword
|
||||
data["swapped_buttons"] = !user.read_preference(/datum/preference/toggle/tgui_swapped_buttons)
|
||||
data["title"] = title
|
||||
data["spellcheck"] = user.read_preference(/datum/preference/toggle/tgui_use_spellcheck)
|
||||
return data
|
||||
|
||||
/datum/tgui_input_text/tgui_data(mob/user)
|
||||
|
||||
@@ -48,7 +48,7 @@
|
||||
"marked-smartypants": "^1.1.9",
|
||||
"react": "^19.1.0",
|
||||
"react-dom": "^19.1.0",
|
||||
"tgui-core": "^5.0.0",
|
||||
"tgui-core": "^5.1.0",
|
||||
"tgui-dev-server": "workspace:*",
|
||||
},
|
||||
},
|
||||
@@ -71,7 +71,7 @@
|
||||
"react": "^19.1.0",
|
||||
"react-dom": "^19.1.0",
|
||||
"tgui": "workspace:*",
|
||||
"tgui-core": "^5.0.0",
|
||||
"tgui-core": "^5.1.0",
|
||||
"tgui-dev-server": "workspace:*",
|
||||
},
|
||||
},
|
||||
@@ -83,7 +83,7 @@
|
||||
"react": "^19.1.0",
|
||||
"react-dom": "^19.1.0",
|
||||
"tgui": "workspace:*",
|
||||
"tgui-core": "^5.0.0",
|
||||
"tgui-core": "^5.1.0",
|
||||
},
|
||||
},
|
||||
"packages/tgui-setup": {
|
||||
@@ -1108,7 +1108,7 @@
|
||||
|
||||
"tgui": ["tgui@workspace:packages/tgui"],
|
||||
|
||||
"tgui-core": ["tgui-core@5.0.0", "", { "dependencies": { "@floating-ui/react": "^0.27.13", "@nozbe/microfuzz": "^1.0.0" }, "peerDependencies": { "react": "^19.1.0", "react-dom": "^19.1.0" } }, "sha512-v03Sds9QjKSLv1WTK3NB1HwZ3Mp+P7FJ0MPdB2QTYnf2UgZG8cinf+SBqo78hOXuLj9iXRMSg5GO5LzaWHBTYQ=="],
|
||||
"tgui-core": ["tgui-core@5.1.0", "", { "dependencies": { "@floating-ui/react": "^0.27.13", "@nozbe/microfuzz": "^1.0.0" }, "peerDependencies": { "react": "^19.1.0", "react-dom": "^19.1.0" } }, "sha512-I6uokZ4hC2UaufOZ9sub2t7ls5F8HtTl2HV/slA4ZqL5hzi2N+lrARoHtPMhi6ZoRZ0ZPJQscqTMdE+Iptcz1A=="],
|
||||
|
||||
"tgui-dev-server": ["tgui-dev-server@workspace:packages/tgui-dev-server"],
|
||||
|
||||
|
||||
@@ -191,11 +191,11 @@ class ChatRenderer {
|
||||
ensureScrollTracking: () => void;
|
||||
highlightParsers:
|
||||
| {
|
||||
highlightWords: string;
|
||||
highlightWords: string[];
|
||||
highlightRegex: RegExp;
|
||||
highlightColor: string;
|
||||
highlightWholeMessage: boolean;
|
||||
highlightBlacklist: string;
|
||||
highlightBlacklist: boolean;
|
||||
blacklistregex: RegExp;
|
||||
}[]
|
||||
| null;
|
||||
|
||||
@@ -12,33 +12,36 @@ const regexParseNode = (params: {
|
||||
regex: RegExp;
|
||||
createNode: (text: string) => Node;
|
||||
captureAdjust?: (str: string) => string;
|
||||
}): { nodes?: HTMLElement; n?: number } => {
|
||||
}): { nodes?: Node[]; n?: number } => {
|
||||
const { node, regex, createNode, captureAdjust } = params;
|
||||
const text = node.textContent || '';
|
||||
const text = node.textContent;
|
||||
|
||||
if (!text || !regex) {
|
||||
return { nodes: [], n: 0 };
|
||||
}
|
||||
|
||||
const textLength = text.length;
|
||||
let nodes;
|
||||
let new_node;
|
||||
let match = regex.exec(text);
|
||||
const nodes: Node[] = [];
|
||||
let fragment: Node | undefined;
|
||||
let new_node: Node;
|
||||
let match: RegExpExecArray | null;
|
||||
let lastIndex = 0;
|
||||
let fragment;
|
||||
let n = 0;
|
||||
let count = 0;
|
||||
// eslint-disable-next-line no-cond-assign
|
||||
while (match !== null) {
|
||||
while (true) {
|
||||
match = regex.exec(text);
|
||||
if (!match) break;
|
||||
n += 1;
|
||||
// Safety check to prevent permanent
|
||||
// client crashing
|
||||
if (++count > 9999) {
|
||||
return {};
|
||||
return { nodes: [], n: 0 };
|
||||
}
|
||||
// Lazy init fragment
|
||||
if (!fragment) {
|
||||
fragment = document.createDocumentFragment();
|
||||
}
|
||||
// Lazy init nodes
|
||||
if (!nodes) {
|
||||
nodes = [];
|
||||
}
|
||||
const matchText = captureAdjust ? captureAdjust(match[0]) : match[0];
|
||||
const matchLength = matchText.length;
|
||||
// If matchText is set to be a substring nested within the original
|
||||
@@ -55,7 +58,6 @@ const regexParseNode = (params: {
|
||||
new_node = createNode(matchText);
|
||||
nodes.push(new_node);
|
||||
fragment.appendChild(new_node);
|
||||
match = regex.exec(text);
|
||||
}
|
||||
if (fragment) {
|
||||
// Insert the remaining unmatched chunk
|
||||
@@ -83,7 +85,7 @@ const regexParseNode = (params: {
|
||||
export const replaceInTextNode =
|
||||
(
|
||||
regex: RegExp,
|
||||
words: string | null,
|
||||
words: string[] | null,
|
||||
createNode: (text: string) => Node,
|
||||
): ((node: Node) => number) =>
|
||||
(node: Node) => {
|
||||
@@ -162,7 +164,7 @@ const createHighlightNode = (text: string): HTMLSpanElement => {
|
||||
export const highlightNode = (
|
||||
node: Node,
|
||||
regex: RegExp,
|
||||
words: string,
|
||||
words: string[],
|
||||
createNode: (text: string) => Node = createHighlightNode,
|
||||
) => {
|
||||
if (!createNode) {
|
||||
|
||||
@@ -8,7 +8,7 @@
|
||||
"react": "^19.1.0",
|
||||
"react-dom": "^19.1.0",
|
||||
"tgui": "workspace:*",
|
||||
"tgui-core": "^5.0.0",
|
||||
"tgui-core": "^5.1.0",
|
||||
"tgui-dev-server": "workspace:*"
|
||||
},
|
||||
"private": true
|
||||
|
||||
@@ -28,6 +28,7 @@ type ByondProps = {
|
||||
minimumWidth: number;
|
||||
lightMode: BooleanLike;
|
||||
scale: BooleanLike;
|
||||
spellcheck: BooleanLike;
|
||||
};
|
||||
|
||||
export function TguiSay() {
|
||||
@@ -38,6 +39,7 @@ export function TguiSay() {
|
||||
const scale = useRef(true);
|
||||
const minimumHeight = useRef(WindowSize.Small);
|
||||
const minimumWidth = useRef(WindowSize.Width);
|
||||
const spellcheck = useRef(true);
|
||||
|
||||
// I initially wanted to make these an object or a reducer, but it's not really worth it.
|
||||
// You lose the granulatity and add a lot of boilerplate.
|
||||
@@ -320,7 +322,7 @@ export function TguiSay() {
|
||||
);
|
||||
minimumHeight.current = data.minimumHeight;
|
||||
minimumWidth.current = minWidth;
|
||||
setLightMode(!!data.lightMode);
|
||||
spellcheck.current = !!data.spellcheck;
|
||||
scale.current = !!data.scale;
|
||||
}
|
||||
|
||||
@@ -388,7 +390,7 @@ export function TguiSay() {
|
||||
{buttonContent}
|
||||
</button>
|
||||
<textarea
|
||||
spellCheck
|
||||
spellCheck={spellcheck.current}
|
||||
autoCorrect="off"
|
||||
className={classes([
|
||||
'textarea',
|
||||
|
||||
@@ -6,7 +6,7 @@
|
||||
"react": "^19.1.0",
|
||||
"react-dom": "^19.1.0",
|
||||
"tgui": "workspace:*",
|
||||
"tgui-core": "^5.0.0"
|
||||
"tgui-core": "^5.1.0"
|
||||
},
|
||||
"private": true
|
||||
}
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
import { useBackend } from 'tgui/backend';
|
||||
import { Button, LabeledList, Section, Stack } from 'tgui-core/components';
|
||||
|
||||
import { useBackend } from '../../backend';
|
||||
import { type ControllerData } from './types';
|
||||
import type { ControllerData } from './types';
|
||||
|
||||
export function OverviewSection(props) {
|
||||
const { act, data } = useBackend<ControllerData>();
|
||||
|
||||
@@ -7,7 +7,7 @@ import {
|
||||
Stack,
|
||||
} from 'tgui-core/components';
|
||||
|
||||
import { type SubsystemData } from './types';
|
||||
import type { SubsystemData } from './types';
|
||||
|
||||
type Props = {
|
||||
subsystem: SubsystemData;
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { type Dispatch } from 'react';
|
||||
import type { Dispatch } from 'react';
|
||||
import {
|
||||
Button,
|
||||
Icon,
|
||||
@@ -49,13 +49,13 @@ export function SubsystemRow(props: Props) {
|
||||
let rangeDisplay = {};
|
||||
if (showBars) {
|
||||
if (sortType === SortType.Cost) {
|
||||
valueDisplay = value.toFixed(2) + 'ms';
|
||||
valueDisplay = `${value.toFixed(2)} ms`;
|
||||
rangeDisplay = {
|
||||
average: [75, 124.99],
|
||||
bad: [125, Infinity],
|
||||
};
|
||||
} else {
|
||||
valueDisplay = value.toFixed(2) + '%';
|
||||
valueDisplay = `${value.toFixed(2)} %`;
|
||||
rangeDisplay = {
|
||||
average: [10, 24.99],
|
||||
bad: [25, Infinity],
|
||||
|
||||
@@ -1,11 +1,10 @@
|
||||
import { type Dispatch, useEffect, useState } from 'react';
|
||||
import { useBackend } from 'tgui/backend';
|
||||
import { Button, Section, Stack, Table } from 'tgui-core/components';
|
||||
|
||||
import { useBackend } from '../../backend';
|
||||
import { SORTING_TYPES } from './constants';
|
||||
import { type FilterState } from './filters';
|
||||
import type { FilterState } from './filters';
|
||||
import { SubsystemRow } from './SubsystemRow';
|
||||
import { type ControllerData, type SubsystemData } from './types';
|
||||
import type { ControllerData, SubsystemData } from './types';
|
||||
|
||||
type Props = {
|
||||
filterOpts: FilterState;
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { type SortType } from './types';
|
||||
import type { SortType } from './types';
|
||||
|
||||
export type FilterState = {
|
||||
ascending: boolean;
|
||||
|
||||
@@ -3,7 +3,7 @@ import { Button, Dropdown, Input, Section, Stack } from 'tgui-core/components';
|
||||
|
||||
import { Window } from '../../layouts';
|
||||
import { SORTING_TYPES } from './constants';
|
||||
import { FilterAction, filterReducer, type FilterState } from './filters';
|
||||
import { FilterAction, type FilterState, filterReducer } from './filters';
|
||||
import { OverviewSection } from './OverviewSection';
|
||||
import { SubsystemDialog } from './SubsystemDialog';
|
||||
import { SubsystemViews } from './SubsystemViews';
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { type BooleanLike } from 'tgui-core/react';
|
||||
import type { BooleanLike } from 'tgui-core/react';
|
||||
|
||||
export type SubsystemData = {
|
||||
can_fire: BooleanLike;
|
||||
|
||||
@@ -83,6 +83,13 @@ export const tgui_say_emotes: FeatureToggle = {
|
||||
component: CheckboxInput,
|
||||
};
|
||||
|
||||
export const TGUI_ENABLE_SPELLCHECK: FeatureToggle = {
|
||||
name: 'TGUI: Spellcheck',
|
||||
category: 'UI',
|
||||
description: 'Enables spellchecking on TGUI text areas and TGUI Say.',
|
||||
component: CheckboxInput,
|
||||
};
|
||||
|
||||
export const tgui_say_height: FeatureNumeric = {
|
||||
name: 'Say: TGUI Height (Lines)',
|
||||
category: 'UI',
|
||||
|
||||
@@ -2,9 +2,8 @@ import { useState } from 'react';
|
||||
import { useBackend } from 'tgui/backend';
|
||||
import { Window } from 'tgui/layouts';
|
||||
import { Box, Section, Stack, TextArea } from 'tgui-core/components';
|
||||
import { isEscape } from 'tgui-core/keys';
|
||||
import { KEY } from 'tgui-core/keys';
|
||||
|
||||
import { isEscape, KEY } from 'tgui-core/keys';
|
||||
import type { BooleanLike } from 'tgui-core/react';
|
||||
import { InputButtons } from './common/InputButtons';
|
||||
import { Loader } from './common/Loader';
|
||||
|
||||
@@ -16,6 +15,7 @@ type TextInputData = {
|
||||
placeholder: string;
|
||||
timeout: number;
|
||||
title: string;
|
||||
spellcheck: BooleanLike;
|
||||
};
|
||||
|
||||
export const sanitizeMultiline = (toSanitize: string) => {
|
||||
@@ -36,6 +36,7 @@ export const TextInputModal = (props) => {
|
||||
placeholder = '',
|
||||
timeout,
|
||||
title,
|
||||
spellcheck,
|
||||
} = data;
|
||||
|
||||
const [input, setInput] = useState(placeholder || '');
|
||||
@@ -80,6 +81,7 @@ export const TextInputModal = (props) => {
|
||||
autoFocus
|
||||
autoSelect
|
||||
fluid
|
||||
spellcheck={!!spellcheck}
|
||||
userMarkup={{ u: '_', i: '|', b: '+' }}
|
||||
height={multiline || input.length >= 30 ? '100%' : '1.8rem'}
|
||||
maxLength={max_length}
|
||||
|
||||
@@ -13,7 +13,7 @@
|
||||
"marked-smartypants": "^1.1.9",
|
||||
"react": "^19.1.0",
|
||||
"react-dom": "^19.1.0",
|
||||
"tgui-core": "^5.0.0",
|
||||
"tgui-core": "^5.1.0",
|
||||
"tgui-dev-server": "workspace:*"
|
||||
},
|
||||
"private": true
|
||||
|
||||
Reference in New Issue
Block a user