@mudlet/mudlet-web 0.3.1 → 0.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +8 -0
- package/dist-lib/assets/qt-resources/index.d.ts +16 -0
- package/dist-lib/branding.d.ts +1 -1
- package/dist-lib/hooks/useMudSession.d.ts +1 -1
- package/dist-lib/hooks/useOutput.d.ts +3 -1
- package/dist-lib/import/defaultPackages.d.ts +35 -2
- package/dist-lib/import/defaults/generic_mapper/generic_mapper.mpackage +0 -0
- package/dist-lib/import/defaults/gui-drop/gui-drop.mpackage +0 -0
- package/dist-lib/import/defaults/{run-lua-code.mpackage → mudlet-base-ui/mudlet-base-ui.mpackage} +0 -0
- package/dist-lib/import/defaults/run-lua-code/run-lua-code.mpackage +0 -0
- package/dist-lib/import/packageExport.d.ts +71 -0
- package/dist-lib/import/packageInstaller.d.ts +4 -1
- package/dist-lib/index.js +45935 -40688
- package/dist-lib/logging/SessionLogger.d.ts +66 -1
- package/dist-lib/map/MapStore.d.ts +32 -4
- package/dist-lib/map/mapImageExport.d.ts +1 -1
- package/dist-lib/map/mapZoom.d.ts +71 -0
- package/dist-lib/mud/ItemIdSequence.d.ts +23 -0
- package/dist-lib/mud/MudSession.d.ts +113 -11
- package/dist-lib/mud/PatternEngine.d.ts +6 -1
- package/dist-lib/mud/commandSplit.d.ts +16 -0
- package/dist-lib/mud/connection/LineAssembler.d.ts +56 -0
- package/dist-lib/mud/connection/MudClient.d.ts +120 -16
- package/dist-lib/mud/connection/TelnetNegotiator.d.ts +39 -0
- package/dist-lib/mud/connection/telnetByteTags.d.ts +35 -0
- package/dist-lib/mud/events.d.ts +19 -4
- package/dist-lib/mud/games/bundledGames.d.ts +29 -0
- package/dist-lib/mud/games/gameIcons.d.ts +5 -0
- package/dist-lib/mud/keybindings/KeyEngine.d.ts +9 -2
- package/dist-lib/mud/keybindings/browserReservedKeys.d.ts +5 -1
- package/dist-lib/mud/keybindings/keyEventTarget.d.ts +17 -0
- package/dist-lib/mud/keybindings/qtKeys.d.ts +2 -0
- package/dist-lib/mud/protocol/charLoginFlow.d.ts +68 -0
- package/dist-lib/mud/protocol/charset.d.ts +27 -5
- package/dist-lib/mud/protocol/constants.d.ts +1 -0
- package/dist-lib/mud/protocol/gmcp.d.ts +19 -3
- package/dist-lib/mud/protocol/index.d.ts +1 -1
- package/dist-lib/mud/protocol/mxp.d.ts +28 -5
- package/dist-lib/mud/replay/ReplayPlayer.d.ts +17 -0
- package/dist-lib/mud/text/Console.d.ts +64 -0
- package/dist-lib/mud/text/FormatState.d.ts +66 -3
- package/dist-lib/mud/text/hyperlinkVisibility.d.ts +35 -0
- package/dist-lib/mud/text/osc8Docs.d.ts +23 -0
- package/dist-lib/mud/text/serverWrap.d.ts +191 -0
- package/dist-lib/mud/timers/TimerEngine.d.ts +43 -12
- package/dist-lib/mud/triggers/TriggerEngine.d.ts +112 -3
- package/dist-lib/scripting/EngineHost.d.ts +56 -3
- package/dist-lib/scripting/IScriptingRuntime.d.ts +16 -0
- package/dist-lib/scripting/MxpFrameManager.d.ts +118 -0
- package/dist-lib/scripting/ScriptingAPI.d.ts +323 -54
- package/dist-lib/scripting/ScriptingEngine.d.ts +180 -23
- package/dist-lib/scripting/http/HttpService.d.ts +51 -1
- package/dist-lib/scripting/lua/LuaRuntime.d.ts +151 -2
- package/dist-lib/scripting/lua/bindings/map.d.ts +0 -12
- package/dist-lib/scripting/lua/utf8Patterns.d.ts +59 -0
- package/dist-lib/storage/index.d.ts +1 -1
- package/dist-lib/storage/persistentStorage.d.ts +10 -0
- package/dist-lib/storage/schema.d.ts +116 -0
- package/dist-lib/styles.css +1 -1
- package/dist-lib/ui/BundledGameGrid.d.ts +21 -0
- package/dist-lib/ui/CommandBar.d.ts +7 -1
- package/dist-lib/ui/ConnectionGrid.d.ts +4 -1
- package/dist-lib/ui/FilePickerModal.d.ts +3 -3
- package/dist-lib/ui/HelpModal.d.ts +11 -0
- package/dist-lib/ui/LogBrowserModal.d.ts +4 -1
- package/dist-lib/ui/PlayerMarkerPreview.d.ts +20 -0
- package/dist-lib/ui/Toolbar.d.ts +2 -1
- package/dist-lib/ui/VfsPickerModal.d.ts +26 -0
- package/dist-lib/ui/components/FileSourceButton.d.ts +47 -0
- package/dist-lib/ui/components/index.d.ts +1 -0
- package/dist-lib/ui/helpTopics.d.ts +19 -0
- package/dist-lib/ui/labels/LabelManager.d.ts +7 -0
- package/dist-lib/ui/layout/ScriptWindow.d.ts +11 -2
- package/dist-lib/ui/markdown.d.ts +10 -1
- package/dist-lib/ui/output/OutputArea.d.ts +11 -1
- package/dist-lib/ui/output/OutputContextMenu.d.ts +3 -1
- package/dist-lib/ui/output/OutputRenderer.d.ts +7 -1
- package/dist-lib/ui/output/OutputSearchBar.d.ts +25 -0
- package/dist-lib/ui/output/StickyOutputPanel.d.ts +5 -1
- package/dist-lib/ui/output/outputSearch.d.ts +130 -0
- package/dist-lib/ui/search/matcher.d.ts +15 -0
- package/dist-lib/ui/search/useDebounced.d.ts +3 -0
- package/dist-lib/ui/tts/TtsManager.d.ts +3 -0
- package/dist-lib/ui/useCommandHistory.d.ts +4 -2
- package/dist-lib/ui/useOpenProfiles.d.ts +26 -0
- package/dist-lib/ui/video/VideoManager.d.ts +17 -0
- package/dist-lib/ui/windows/WindowManager.d.ts +132 -2
- package/dist-lib/ui/windows/panels/MapPanel.d.ts +4 -1
- package/dist-lib/ui/windows/panels/PackageExportModal.d.ts +18 -0
- package/dist-lib/ui/windows/panels/TextPanel.d.ts +3 -1
- package/dist-lib/ui/windows/types.d.ts +35 -0
- package/dist-lib/utils/describeThrown.d.ts +22 -0
- package/dist-lib/utils/fontLoader.d.ts +5 -0
- package/dist-lib/vite.js +22 -0
- package/package.json +10 -6
- package/dist-lib/scripting/lua/mudlet-lua/generic-mapper/generic_mapper.mpackage +0 -0
- package/dist-lib/ui/windows/panels/VfsModulePickerModal.d.ts +0 -8
|
@@ -3,7 +3,7 @@ import { AnsiAwareBuffer } from "../text/FormatState";
|
|
|
3
3
|
import { type ChunkProcessor } from "../triggers/ChunkProcessor";
|
|
4
4
|
import type { MudClientEvents } from "../events";
|
|
5
5
|
export type { MudClientEvents } from "../events";
|
|
6
|
-
export { SUPPORTED_SERVER_ENCODINGS } from "../protocol";
|
|
6
|
+
export { SUPPORTED_SERVER_ENCODINGS, DEFAULT_SERVER_ENCODING, canonicalServerEncoding, canEncodeForServer } from "../protocol";
|
|
7
7
|
export interface MudClientOptions {
|
|
8
8
|
url: string;
|
|
9
9
|
mccpEnabled?: boolean;
|
|
@@ -88,6 +88,51 @@ export interface MudClientOptions {
|
|
|
88
88
|
* of each GA-terminated data block — the IRE-server bug Mudlet patches in
|
|
89
89
|
* `cTelnet::gotPrompt`. See LineAssembler. */
|
|
90
90
|
fixUnnecessaryLinebreaks?: boolean;
|
|
91
|
+
/** Mudlet's `Host::mUndoServerWrap` — rejoin the lines the game wrapped
|
|
92
|
+
* itself, so triggers and rendering see whole logical lines. Default false.
|
|
93
|
+
* See LineAssembler and mud/text/serverWrap.ts. */
|
|
94
|
+
undoServerWrap?: boolean;
|
|
95
|
+
/** The column that game wraps at (`Host::mUndoServerWrapWidth`, default 80).
|
|
96
|
+
* Only consulted while {@link undoServerWrap} is on. */
|
|
97
|
+
undoServerWrapWidth?: number;
|
|
98
|
+
/** Mudlet's `setConfig("inputLineStrictUnixEndings", …)` (host flag
|
|
99
|
+
* `mUSE_UNIX_EOL`). Default false. When true a submitted command is
|
|
100
|
+
* terminated with a bare `\n` instead of the telnet-standard `\r\n`
|
|
101
|
+
* (`cTelnet::sendData` appends the CR only when the flag is off) — some
|
|
102
|
+
* Unix-y servers treat the CR as part of the command. */
|
|
103
|
+
inputLineStrictUnixEndings?: boolean;
|
|
104
|
+
/** Mudlet's `setConfig("specialForceGAOff", …)` (host flag `mFORCE_GA_OFF`).
|
|
105
|
+
* Default false. When true an inbound IAC GA / IAC EOR is *not* treated as
|
|
106
|
+
* a prompt marker: the session never latches into GA-driven mode and the
|
|
107
|
+
* marker becomes a plain newline in the data stream, exactly as
|
|
108
|
+
* `cTelnet::processSocketData` does in its `else` branch. For servers whose
|
|
109
|
+
* GA placement is wrong often enough that prompt detection does more harm
|
|
110
|
+
* than good. Read once per connect (Mudlet snapshots it in `connectIt`), so
|
|
111
|
+
* a mid-session change applies on the next dial. */
|
|
112
|
+
specialForceGAOff?: boolean;
|
|
113
|
+
/** Mudlet's `setConfig("promptForVersionInTTYPE", …)` (host flag
|
|
114
|
+
* `mPromptedForVersionInTTYPE`). Default false. Latches once the KaVir
|
|
115
|
+
* auto-detect has had its say for this profile, so a user who then turns
|
|
116
|
+
* `versionInTTYPE` back off isn't overridden on the next connect. */
|
|
117
|
+
promptForVersionInTTYPE?: boolean;
|
|
118
|
+
/** Mudlet's `setConfig("promptForMXPProcessorOn", …)` (host flag
|
|
119
|
+
* `mPromptedForMXPProcessorOn`). Default false. Latches once the in-band
|
|
120
|
+
* MXP auto-detect has fired for this profile; together with
|
|
121
|
+
* `specialForceMXPProcessorOn` it decides whether an `ESC[<n>z` from a
|
|
122
|
+
* server that never negotiated option 91 may still start MXP. */
|
|
123
|
+
promptForMXPProcessorOn?: boolean;
|
|
124
|
+
/** Mudlet's `setConfig("specialForceMXPProcessorOn", …)` (host flag
|
|
125
|
+
* `mForceMXPProcessorOn`). Default false. Only consulted here for the
|
|
126
|
+
* in-band-detection gate above — the parser-side effect lives in
|
|
127
|
+
* ScriptingEngine, which owns the MXP processor. */
|
|
128
|
+
specialForceMXPProcessorOn?: boolean;
|
|
129
|
+
/** Mudlet's `setConfig("versionInTTYPE", …)` (host flag `mVersionInTTYPE`).
|
|
130
|
+
* Default false. When true the first TTYPE cycle value carries our version
|
|
131
|
+
* after the client name (`MUDLET-WEB 1.2.3`). Off by default because the
|
|
132
|
+
* period is not a legal TTYPE character per RFC 1091 — but servers running
|
|
133
|
+
* KaVir's protocol snippet parse a version out of it and fall back to 16
|
|
134
|
+
* colours without one, so it's opt-in rather than absent. */
|
|
135
|
+
versionInTTYPE?: boolean;
|
|
91
136
|
/** WebSocket subprotocols to advertise in the opening handshake's
|
|
92
137
|
* `Sec-WebSocket-Protocol` header (RFC 6455), in preference order — the
|
|
93
138
|
* server selects at most one. Mutually-exclusive stream *modes*, not layers:
|
|
@@ -117,6 +162,8 @@ export declare const MUD_TELNET_SUBPROTOCOL = "telnet.mudstandards.org";
|
|
|
117
162
|
* GMCP/MSDP/MSSP subnegotiation streams.
|
|
118
163
|
*/
|
|
119
164
|
export declare class MudClient {
|
|
165
|
+
/** The live WebSocket, or null when there is none — before the first
|
|
166
|
+
* connect, and from the moment disconnect() lets go of one. */
|
|
120
167
|
private socket;
|
|
121
168
|
private readonly eventBus;
|
|
122
169
|
private readonly chunkProcessor;
|
|
@@ -130,8 +177,12 @@ export declare class MudClient {
|
|
|
130
177
|
private readonly negotiator;
|
|
131
178
|
/** Latches once `sysCharacterModeDetected` has fired for this connection so
|
|
132
179
|
* the warning isn't repeated. Reset on each connect(). See
|
|
133
|
-
* {@link
|
|
180
|
+
* {@link checkCharacterModePattern}. */
|
|
134
181
|
private charModeDetected;
|
|
182
|
+
/** Pending character-at-a-time verdict, armed by a submitted game command
|
|
183
|
+
* while ECHO+SGA are active and cancelled if the server releases ECHO
|
|
184
|
+
* first. Null when nothing is in flight. */
|
|
185
|
+
private charModeTimer;
|
|
135
186
|
/** Byte↔char codec for the session (inbound streaming decoder + outgoing
|
|
136
187
|
* encoding). Swapped between encodings by the CHARSET handler. */
|
|
137
188
|
private readonly codec;
|
|
@@ -164,21 +215,68 @@ export declare class MudClient {
|
|
|
164
215
|
private readonly mspParser;
|
|
165
216
|
/** WebSocket subprotocols advertised on connect (see MudClientOptions). */
|
|
166
217
|
private readonly subprotocols;
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
*
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
*
|
|
173
|
-
*
|
|
174
|
-
*
|
|
175
|
-
*
|
|
176
|
-
private
|
|
218
|
+
/** Mudlet `mUSE_UNIX_EOL` — terminate submitted commands with a bare `\n`.
|
|
219
|
+
* Read on every send, so a change applies to the next command (Mudlet reads
|
|
220
|
+
* the host flag in `sendData` too). */
|
|
221
|
+
private strictUnixEndings;
|
|
222
|
+
/** Mudlet `mFORCE_GA_OFF` — see MudClientOptions.specialForceGAOff. A live
|
|
223
|
+
* session keeps parsing with the value it connected with (Mudlet snapshots
|
|
224
|
+
* the host flag into cTelnet at `connectIt`), which here falls out of
|
|
225
|
+
* MudSession building a fresh client per connect. An unconnected one takes
|
|
226
|
+
* the change straight away — see {@link setForceGaOff}. */
|
|
227
|
+
private forceGaOff;
|
|
228
|
+
/** Handed to the telnet sequence parser and mutated in place, so the parser
|
|
229
|
+
* reads the current setting rather than the one it was built with. */
|
|
230
|
+
private readonly telnetParserOpts;
|
|
231
|
+
constructor({ url, mccpEnabled, commandEcho, chunkProcessor, promptTimeoutMs, gmcpEnabled, mttsEnabled, msdpEnabled, msspEnabled, charsetEnabled, mspEnabled, mxpEnabled, mnesEnabled, newEnvironEnabled, secureTransport, screenReaderAdvertised, nawsEnabled, fixUnnecessaryLinebreaks, undoServerWrap, undoServerWrapWidth, inputLineStrictUnixEndings, specialForceGAOff, versionInTTYPE, promptForVersionInTTYPE, promptForMXPProcessorOn, specialForceMXPProcessorOn, subprotocols, }: MudClientOptions, eventBus: EventBus<MudClientEvents>);
|
|
232
|
+
/** Mudlet-parity character-at-a-time detection (cTelnet::sendData's
|
|
233
|
+
* `armCharacterModeDetection`). ECHO+SGA on its own is *not* the signature:
|
|
234
|
+
* an ordinary line-mode server masking a password negotiates exactly the
|
|
235
|
+
* same pair. The two are told apart by behaviour, so detection is armed
|
|
236
|
+
* only by a submitted game command and only decides {@link
|
|
237
|
+
* CHARACTER_MODE_DETECT_MS} later — a password mask sends WONT ECHO right
|
|
238
|
+
* after the masked line and cancels it first.
|
|
239
|
+
*
|
|
240
|
+
* Re-armed on every game command so the window always measures from the
|
|
241
|
+
* most recent submission. */
|
|
242
|
+
private armCharacterModeDetection;
|
|
243
|
+
private cancelCharacterModeDetection;
|
|
244
|
+
/** The armed window elapsed with ECHO+SGA still active — a full input line
|
|
245
|
+
* was submitted without the server releasing echo, which a password prompt
|
|
246
|
+
* never does. Raise `sysCharacterModeDetected` once per connection so the
|
|
247
|
+
* UI / scripts can warn the user.
|
|
248
|
+
*
|
|
249
|
+
* Accepted limitation (same as Mudlet's): this can't tell genuine
|
|
250
|
+
* character-at-a-time from the rarer cases of a buggy password prompt that
|
|
251
|
+
* never sends WONT ECHO, or a line-mode server using persistent
|
|
252
|
+
* server-side echo. We stay in line mode regardless and the message is
|
|
253
|
+
* only advisory. */
|
|
254
|
+
private checkCharacterModePattern;
|
|
177
255
|
setMccpEnabled(enabled: boolean): void;
|
|
178
256
|
isMccpEnabled(): boolean;
|
|
179
257
|
/** Mudlet `setConfig("fixUnnecessaryLinebreaks", …)`. Takes effect on the
|
|
180
258
|
* next GA-driven block; never retroactive. */
|
|
181
259
|
setFixUnnecessaryLinebreaks(enabled: boolean): void;
|
|
260
|
+
/**
|
|
261
|
+
* Mudlet `setConfig("specialForceGAOff", …)`. Only an UNCONNECTED client
|
|
262
|
+
* takes the change: a live session has to keep parsing telnet the way it
|
|
263
|
+
* connected, or a GA mid-stream would suddenly mean something else. Mudlet
|
|
264
|
+
* draws the same line — `cacheHostSettings()` is re-run from setConfig only
|
|
265
|
+
* while the socket is unconnected, and otherwise at the next connect.
|
|
266
|
+
*/
|
|
267
|
+
setForceGaOff(enabled: boolean): void;
|
|
268
|
+
/** Mudlet `setConfig("undoServerWrap", …)`. Live: the next server line is
|
|
269
|
+
* judged under the new setting. */
|
|
270
|
+
setUndoServerWrap(enabled: boolean): void;
|
|
271
|
+
/** Mudlet `setConfig("undoServerWrapWidth", …)`. */
|
|
272
|
+
setUndoServerWrapWidth(width: number): void;
|
|
273
|
+
/** Commit a line held for a wrap continuation whose flush delay has passed.
|
|
274
|
+
* See {@link LineAssembler.pumpServerWrapDue}. */
|
|
275
|
+
pumpServerWrapDue(now?: number): boolean;
|
|
276
|
+
/** Mudlet `setConfig("inputLineStrictUnixEndings", …)`. Live: `cTelnet::
|
|
277
|
+
* sendData` reads the host flag per send, so the next command submitted
|
|
278
|
+
* uses the new terminator. */
|
|
279
|
+
setInputLineStrictUnixEndings(enabled: boolean): void;
|
|
182
280
|
/** Mudlet `addSupportedTelnetOption(option)`. See TelnetNegotiator. */
|
|
183
281
|
addSupportedTelnetOption(option: number): boolean;
|
|
184
282
|
setPromptTimeoutMs(ms: number): void;
|
|
@@ -200,7 +298,11 @@ export declare class MudClient {
|
|
|
200
298
|
isSocketOpen(): boolean;
|
|
201
299
|
isPasswordMode(): boolean;
|
|
202
300
|
shouldEchoCommand(): boolean;
|
|
203
|
-
|
|
301
|
+
/** `isGameCommand` mirrors `cTelnet::sendData`'s third argument: only a real
|
|
302
|
+
* game command (typed or from a script's `send()`) may arm
|
|
303
|
+
* character-at-a-time detection. Credentials and internal protocol replies
|
|
304
|
+
* route through here too and must not. */
|
|
305
|
+
send(message: string, isGameCommand?: boolean): void;
|
|
204
306
|
private sendRaw;
|
|
205
307
|
/** Encodes a Latin-1 byte-string to raw bytes and sends it as a binary
|
|
206
308
|
* WebSocket frame. The proxy worker expects binary, not base64. Every
|
|
@@ -245,9 +347,11 @@ export declare class MudClient {
|
|
|
245
347
|
* (the zMUD generic out-of-band channel) and sends it raw. Returns false
|
|
246
348
|
* when the socket isn't open. */
|
|
247
349
|
sendTelnetChannel102(msg: string): boolean;
|
|
248
|
-
/** Frame
|
|
249
|
-
*
|
|
250
|
-
*
|
|
350
|
+
/** Frame an `IAC SB <opt> <payload> IAC SE` subnegotiation and send it.
|
|
351
|
+
* `payload` must already be a Latin-1 byte-string (each char → one byte)
|
|
352
|
+
* with any IAC handled — the framing is all this does, since ATCP and
|
|
353
|
+
* channel 102 need different byte treatments. Shared by sendATCP /
|
|
354
|
+
* sendTelnetChannel102. */
|
|
251
355
|
private sendSubnegotiation;
|
|
252
356
|
/** Mudlet `getServerEncoding()`. The IANA name of the decoder currently
|
|
253
357
|
* applied to the inbound stream — 'utf-8' until CHARSET negotiation (or an
|
|
@@ -18,6 +18,25 @@ export interface TelnetNegotiatorFlags {
|
|
|
18
18
|
* key. Default false; some MUDs adjust their output (e.g. suppress ASCII
|
|
19
19
|
* art, add extra room-description detail) when this is set. */
|
|
20
20
|
screenReaderAdvertised: boolean;
|
|
21
|
+
/** Whether the first TTYPE cycle value carries our version after the client
|
|
22
|
+
* name — Mudlet's `versionInTTYPE` config key (`mVersionInTTYPE`). Default
|
|
23
|
+
* false: RFC 1091 doesn't permit the period, so Mudlet stopped sending it
|
|
24
|
+
* in 2024. Servers running KaVir's protocol snippet want it anyway (without
|
|
25
|
+
* a version they assume 1.0 and cap colour support at 16), which is what
|
|
26
|
+
* the KaVir auto-detect below turns it on for. */
|
|
27
|
+
versionInTTYPE: boolean;
|
|
28
|
+
/** Whether this profile has already been through the KaVir auto-detect —
|
|
29
|
+
* Mudlet's `promptForVersionInTTYPE` config key (`mPromptedForVersionInTTYPE`).
|
|
30
|
+
* When true the detector below is disabled, so a user who turned
|
|
31
|
+
* `versionInTTYPE` back off is not overridden on every reconnect. */
|
|
32
|
+
versionInTTYPEPrompted: boolean;
|
|
33
|
+
/** Whether an in-band `ESC[<n>z` may still auto-start MXP on a server that
|
|
34
|
+
* never negotiated telnet option 91. Mudlet gates its equivalent scan on
|
|
35
|
+
* `mForceMXPProcessorOn || !mPromptedForMXPProcessorOn`
|
|
36
|
+
* (`cTelnet::gotRest`): once the auto-detect has fired for a profile, only
|
|
37
|
+
* the forced-on state keeps it live — so a user who then turns
|
|
38
|
+
* `specialForceMXPProcessorOn` off is not re-overridden every connect. */
|
|
39
|
+
mxpInBandDetectionEnabled: boolean;
|
|
21
40
|
}
|
|
22
41
|
export interface TelnetNegotiatorHooks {
|
|
23
42
|
sendRaw(data: string): void;
|
|
@@ -30,6 +49,10 @@ export interface TelnetNegotiatorHooks {
|
|
|
30
49
|
/** Current inbound encoding (IANA label) — drives the MTTS UTF-8 bit and
|
|
31
50
|
* the MNES/NEW-ENVIRON CHARSET variable. */
|
|
32
51
|
getEncoding(): string;
|
|
52
|
+
/** The server's option-negotiation order matched KaVir's protocol snippet —
|
|
53
|
+
* it wants a version in our TTYPE reply. Fired at most once per connection;
|
|
54
|
+
* the owner turns `versionInTTYPE` on and redials. */
|
|
55
|
+
onKaVirProtocolDetected(): void;
|
|
33
56
|
}
|
|
34
57
|
/**
|
|
35
58
|
* Telnet option negotiation for a MUD session. Owns the WILL/WONT/DO/DONT
|
|
@@ -76,6 +99,15 @@ export declare class TelnetNegotiator {
|
|
|
76
99
|
* telnet handshake, so the in-band signal is the reliable trigger. Reset on
|
|
77
100
|
* each connect(). */
|
|
78
101
|
private mxpStarted;
|
|
102
|
+
/** Rolling window of the last {@link KAVIR_NEGOTIATION_ORDER}`.length`
|
|
103
|
+
* options the server sent us a WILL/DO for, oldest first — Mudlet's
|
|
104
|
+
* `mNegotiationOrder`. Compared against the KaVir fingerprint after each
|
|
105
|
+
* push. Reset on each connect(). */
|
|
106
|
+
private negotiationOrder;
|
|
107
|
+
/** Latches once the KaVir fingerprint has matched this connection, so the
|
|
108
|
+
* detector fires the hook at most once even though a server may keep
|
|
109
|
+
* re-offering options. */
|
|
110
|
+
private kaVirDetected;
|
|
79
111
|
/** True once we've sent IAC WILL NAWS this session (proactively on connect,
|
|
80
112
|
* or in response to a server-initiated IAC DO NAWS), so we don't re-offer. */
|
|
81
113
|
private nawsWillSent;
|
|
@@ -141,6 +173,13 @@ export declare class TelnetNegotiator {
|
|
|
141
173
|
* supported-options registry answers every occurrence; anything left is
|
|
142
174
|
* surfaced as a `telnet.event`. */
|
|
143
175
|
private handleNegotiationCommand;
|
|
176
|
+
/** Mudlet `cTelnet::trackKaVirNegotiation`. Records the option of each
|
|
177
|
+
* inbound WILL/DO in a rolling window and fires the hook the first time the
|
|
178
|
+
* window equals the KaVir fingerprint. Recording happens before the
|
|
179
|
+
* per-frame response dedupe, so the order seen here is the order the server
|
|
180
|
+
* actually sent — the same thing Mudlet feeds its own tracker from
|
|
181
|
+
* `processTelnetCommand`. */
|
|
182
|
+
private trackKaVirNegotiation;
|
|
144
183
|
private respondToKnownOption;
|
|
145
184
|
/** Raise `telnet.event` for an SB of an option we neither handle natively
|
|
146
185
|
* nor auto-negotiate (type 5 in Mudlet's sysTelnetEvent mapping). */
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Mudlet's `<XX>` byte placeholders for `feedTelnet(data)` —
|
|
3
|
+
* `TLuaInterpreter::decodeBytes`.
|
|
4
|
+
*
|
|
5
|
+
* Lua strings are text, and the bytes a telnet stream is made of mostly are not:
|
|
6
|
+
* `\xff\xf9` typed into a script is awkward to read and easy to get wrong, and a
|
|
7
|
+
* profile that saves scripts as XML has to survive round-tripping them. So
|
|
8
|
+
* Mudlet lets the data name its control bytes instead — `<T_IAC><T_GA>` for a
|
|
9
|
+
* prompt marker, `<ESC>` for the start of an ANSI sequence — and decodes them
|
|
10
|
+
* here before the bytes reach the parser.
|
|
11
|
+
*
|
|
12
|
+
* Anything that isn't a known tag is passed through unchanged, so ordinary text
|
|
13
|
+
* containing `<` survives; `<<` and `>>` are the escapes for a literal one.
|
|
14
|
+
*/
|
|
15
|
+
/**
|
|
16
|
+
* Version of the tag table, as Mudlet's `decodeBytes` reports it: feeding the
|
|
17
|
+
* empty string yields this number as text rather than nothing, so a script can
|
|
18
|
+
* ask which tags it can count on.
|
|
19
|
+
*/
|
|
20
|
+
export declare const TELNET_BYTE_TAG_TABLE_VERSION = 1;
|
|
21
|
+
/**
|
|
22
|
+
* Decode Mudlet's `<XX>` byte placeholders into the bytes they name, as
|
|
23
|
+
* `feedTelnet` does before handing data to the telnet parser.
|
|
24
|
+
*
|
|
25
|
+
* The result is a byte-string (each code unit ≤ 0xFF), which is what the inbound
|
|
26
|
+
* pipeline takes — the same shape a decoded WebSocket frame arrives in.
|
|
27
|
+
*
|
|
28
|
+
* - `<<` yields a literal `<`, `>>` a literal `>`.
|
|
29
|
+
* - An unknown `<…>` is left exactly as written, so prose and markup pass
|
|
30
|
+
* through: `<b>bold</b>` is text, not a failed decode.
|
|
31
|
+
* - An unclosed `<` is likewise just a `<`.
|
|
32
|
+
* - The empty string yields the tag table's version number as text, which is how
|
|
33
|
+
* a script asks what this build understands.
|
|
34
|
+
*/
|
|
35
|
+
export declare function decodeTelnetByteTags(input: string): string;
|
package/dist-lib/mud/events.d.ts
CHANGED
|
@@ -189,11 +189,21 @@ export type MudClientEvents = {
|
|
|
189
189
|
* (`'SUPPRESS_GO_AHEAD'` or `'LINEMODE'`). */
|
|
190
190
|
'protocol.rejected': [protocol: string];
|
|
191
191
|
/** Mudlet `sysCharacterModeDetected`. Fires once per connection when the
|
|
192
|
-
* server has both asked to suppress go-ahead (IAC WILL SGA) *and*
|
|
193
|
-
* server-side echo
|
|
194
|
-
* a line-based client, can't
|
|
195
|
-
*
|
|
192
|
+
* server has both asked to suppress go-ahead (IAC WILL SGA) *and* kept
|
|
193
|
+
* server-side echo on across a submitted game command — the
|
|
194
|
+
* character-at-a-time signature that mudix, a line-based client, can't
|
|
195
|
+
* drive well. The three-second delay is what separates it from an ordinary
|
|
196
|
+
* password mask, which negotiates the same pair but releases echo as soon
|
|
197
|
+
* as the masked line is in. Lets scripts / the UI warn the user that input
|
|
198
|
+
* may not behave as expected. */
|
|
196
199
|
'charmode.detected': void;
|
|
200
|
+
/** The server's telnet option-negotiation order matched KaVir's protocol
|
|
201
|
+
* snippet (Mudlet `cTelnet::trackKaVirNegotiation`). Such servers read a
|
|
202
|
+
* decimal version out of our TTYPE client-name reply and fall back to 16
|
|
203
|
+
* colours without one, so the owner switches `versionInTTYPE` on and
|
|
204
|
+
* redials. Fires at most once per connection, and never once the profile's
|
|
205
|
+
* `promptForVersionInTTYPE` latch is set. */
|
|
206
|
+
'kavir.detected': void;
|
|
197
207
|
} & Record<string, any>;
|
|
198
208
|
export type MudEvents = MudClientEvents & {
|
|
199
209
|
'status': [status: SessionStatus];
|
|
@@ -207,6 +217,11 @@ export type MudEvents = MudClientEvents & {
|
|
|
207
217
|
'script.clearcmd': void;
|
|
208
218
|
'script.selectcmd': void;
|
|
209
219
|
'script.cmdlinesuggestions': [items: string[]];
|
|
220
|
+
/** Words Tab completion must never offer, whatever list they came from. */
|
|
221
|
+
'script.cmdlineblacklist': [items: string[]];
|
|
222
|
+
/** Whether the main command bar's history is persisted at all
|
|
223
|
+
* (setSaveCommandHistory); the size cap stays a separate setting. */
|
|
224
|
+
'script.savecommandhistory': [save: boolean];
|
|
210
225
|
'script.openvfs': [path: string];
|
|
211
226
|
/** Fired by ScriptingAPI when Lua calls `invokeFileDialog(...)`. The UI
|
|
212
227
|
* (ProfileSession) shows the in-app VFS picker and resolves the request
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
/** One entry of Mudlet's bundled-game catalogue (its C++ `GameDetail`). */
|
|
2
|
+
export interface BundledGame {
|
|
3
|
+
name: string;
|
|
4
|
+
hostUrl: string;
|
|
5
|
+
port: number;
|
|
6
|
+
tlsEnabled: boolean;
|
|
7
|
+
/** Small HTML fragment of website/forum/Discord links. */
|
|
8
|
+
websiteInfo: string;
|
|
9
|
+
/** Qt resource path of the game's icon, kept as the upstream identifier. */
|
|
10
|
+
icon: string;
|
|
11
|
+
/** Filename of the copy vendored in ./icons/, when one was available.
|
|
12
|
+
* Resolve it with `gameIconUrl()` rather than building a path by hand —
|
|
13
|
+
* the bundler only emits assets it can see referenced. */
|
|
14
|
+
iconFile?: string;
|
|
15
|
+
description: string;
|
|
16
|
+
/** The game's own loader installs its full interface, so the generic
|
|
17
|
+
* starter UI is not preinstalled for it. */
|
|
18
|
+
providesOwnUi?: boolean;
|
|
19
|
+
/** Other hostnames the game answers on. */
|
|
20
|
+
alternateHostUrls?: string[];
|
|
21
|
+
}
|
|
22
|
+
export declare const BUNDLED_GAMES: readonly BundledGame[];
|
|
23
|
+
/** The bundled game called `name`, matched the way Mudlet matches it
|
|
24
|
+
* (TGameDetails::findGame — exact, case-sensitive). */
|
|
25
|
+
export declare function findBundledGame(name: string): BundledGame | null;
|
|
26
|
+
/** Whether the game reachable at `hostUrl` installs its own full interface,
|
|
27
|
+
* in which case the generic starter UI is not preinstalled (Mudlet's
|
|
28
|
+
* TGameDetails::gameProvidesOwnUi). */
|
|
29
|
+
export declare function gameProvidesOwnUi(hostUrl: string): boolean;
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import { type BundledGame } from './bundledGames';
|
|
2
|
+
/** URL of a bundled game's logo, or null when it has none vendored. Accepts the
|
|
3
|
+
* entry or its exact name, so a caller holding only a profile name (which is
|
|
4
|
+
* the game's name for a profile made from the catalogue) can ask too. */
|
|
5
|
+
export declare function gameIconUrl(game: BundledGame | string | undefined): string | null;
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { ItemIdSequence } from '../ItemIdSequence';
|
|
1
2
|
import type { KeyNode } from '../../storage/schema';
|
|
2
3
|
export type { KeyNode };
|
|
3
4
|
type TempFn = () => void;
|
|
@@ -9,8 +10,11 @@ export interface KeyCodeInfo {
|
|
|
9
10
|
export declare class KeyEngine {
|
|
10
11
|
private readonly temp;
|
|
11
12
|
private perm;
|
|
12
|
-
|
|
13
|
-
|
|
13
|
+
/** Shared with every other engine in the profile — see ItemIdSequence. */
|
|
14
|
+
private idSeq;
|
|
15
|
+
setIdSequence(seq: ItemIdSequence): void;
|
|
16
|
+
/** Number of live session-scoped temp keys (Mudlet `getProfileStats` temp
|
|
17
|
+
* count). Killed-but-unreaped keys are not live and don't count. */
|
|
14
18
|
get tempCount(): number;
|
|
15
19
|
addTemp(key: string, modifiers: string[], fn: TempFn, qt?: {
|
|
16
20
|
keyCode: number;
|
|
@@ -29,6 +33,9 @@ export declare class KeyEngine {
|
|
|
29
33
|
*/
|
|
30
34
|
getKeyCode(idOrName: number | string): KeyCodeInfo | null;
|
|
31
35
|
killKey(id: number): boolean;
|
|
36
|
+
/** Free every key killed since the last call. Runs once per processed line
|
|
37
|
+
* batch, mirroring the deferred cleanup Mudlet's TKeyUnit does. */
|
|
38
|
+
reapKilled(): void;
|
|
32
39
|
processTemp(event: KeyboardEvent): boolean;
|
|
33
40
|
loadPerm(keybindings: KeyNode[]): void;
|
|
34
41
|
matchPerm(event: KeyboardEvent): KeyNode | null;
|
|
@@ -25,7 +25,11 @@ export interface ReservedKeyWarning {
|
|
|
25
25
|
}
|
|
26
26
|
/** Platform accelerator — browser shortcuts use Cmd (meta) on macOS, Ctrl elsewhere. */
|
|
27
27
|
export type Accel = 'ctrl' | 'meta';
|
|
28
|
-
/** Detect the platform accelerator modifier
|
|
28
|
+
/** Detect the platform accelerator modifier, from `navigator.platform` on every
|
|
29
|
+
* call. Note that a `navigator` exists under vitest's node environment too, and
|
|
30
|
+
* reports the real host — so this is not a Ctrl fallback in tests, and a test
|
|
31
|
+
* that hard-codes one accelerator will pass on CI and fail on a Mac. Callers
|
|
32
|
+
* that need a fixed platform should pass `accel` explicitly. */
|
|
29
33
|
export declare function detectAccel(): Accel;
|
|
30
34
|
/** Render a keybinding as a display combo like "Ctrl+Shift+I". */
|
|
31
35
|
export declare function formatKeyCombo(node: Pick<KeyNode, 'key' | 'modifiers'>): string;
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Whether a keydown belongs to the focused text widget rather than to the
|
|
3
|
+
* keybinding engine.
|
|
4
|
+
*
|
|
5
|
+
* The MUD command line is a `<textarea class="command-input">` (an `<input>`
|
|
6
|
+
* of the same class in password mode) and holds focus for essentially the
|
|
7
|
+
* whole session. So the usual "don't hijack keys while the user is typing"
|
|
8
|
+
* guard — `tagName === 'TEXTAREA'` — cannot be applied to it: it is true
|
|
9
|
+
* almost always, and it silently disables every keybinding in the profile.
|
|
10
|
+
* Typing a command is the app's resting state, not a text-entry mode that
|
|
11
|
+
* should own every hotkey.
|
|
12
|
+
*
|
|
13
|
+
* Real text entry elsewhere — the Lua script editor (CodeMirror, so
|
|
14
|
+
* `contentEditable`), a modal's form field, the script tree's filter box —
|
|
15
|
+
* does keep the event to itself.
|
|
16
|
+
*/
|
|
17
|
+
export declare function isTextEntryTarget(target: EventTarget | null): boolean;
|
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
/** Qt::KeypadModifier — set by Mudlet when a binding came from the numpad. */
|
|
2
2
|
export declare const QT_KEYPAD_MODIFIER = 536870912;
|
|
3
|
+
/** Qt::Key_unknown — what Mudlet stores for a key item with nothing bound to it. */
|
|
4
|
+
export declare const QT_KEY_UNKNOWN = 33554431;
|
|
3
5
|
/**
|
|
4
6
|
* Translate a Qt::Key integer (or already-translated DOM `KeyboardEvent.code`
|
|
5
7
|
* string) into a DOM `KeyboardEvent.code`. Mudlet `tempKey` accepts both;
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* GMCP `Char.Login` flow decisions.
|
|
3
|
+
*
|
|
4
|
+
* The server sends `Char.Login.Default` to ask for credentials and then waits,
|
|
5
|
+
* withholding its text login prompt until the client answers. Answering is
|
|
6
|
+
* therefore mandatory — every path here ends in either a credentials reply or a
|
|
7
|
+
* popup that will produce one. `Char.Login.Result` reports the outcome, and a
|
|
8
|
+
* server that rejects an attempt commonly re-sends `Char.Login.Default` to ask
|
|
9
|
+
* again, so these rules run repeatedly within one connection.
|
|
10
|
+
*
|
|
11
|
+
* Mirrors Mudlet's `GMCPAuthenticator` (GMCPAuthenticator.cpp). Kept free of
|
|
12
|
+
* React and session plumbing so the rules can be tested directly; the caller
|
|
13
|
+
* supplies the per-connection state.
|
|
14
|
+
*/
|
|
15
|
+
/** What to do about a `Char.Login.Default` request. */
|
|
16
|
+
export type CharLoginAction =
|
|
17
|
+
/** Reply with the empty `{}` form — "no credentials, use your next method". */
|
|
18
|
+
{
|
|
19
|
+
kind: 'decline';
|
|
20
|
+
}
|
|
21
|
+
/** Send stored credentials without troubling the player. */
|
|
22
|
+
| {
|
|
23
|
+
kind: 'autofill';
|
|
24
|
+
account: string;
|
|
25
|
+
password: string;
|
|
26
|
+
}
|
|
27
|
+
/** Raise the credentials popup. */
|
|
28
|
+
| {
|
|
29
|
+
kind: 'prompt';
|
|
30
|
+
};
|
|
31
|
+
export interface CharLoginRequestState {
|
|
32
|
+
/** The `type` list from `Char.Login.Default`; empty when the server sent none. */
|
|
33
|
+
methods: string[];
|
|
34
|
+
/** The player chose "Use text login" earlier this connection. */
|
|
35
|
+
declined: boolean;
|
|
36
|
+
/** Credentials have already been sent once this connection (stored or typed). */
|
|
37
|
+
attempted: boolean;
|
|
38
|
+
/** Stored/in-memory credentials, if any. */
|
|
39
|
+
account?: string;
|
|
40
|
+
password?: string;
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Decide how to answer a `Char.Login.Default`.
|
|
44
|
+
*
|
|
45
|
+
* The one automatic attempt per connection is the load-bearing rule: it makes a
|
|
46
|
+
* saved login silent when it works, and guarantees that a *wrong* saved login
|
|
47
|
+
* turns into a visible popup instead of a silent send-reject-send loop against
|
|
48
|
+
* the server's repeated asks.
|
|
49
|
+
*/
|
|
50
|
+
export declare function decideCharLoginRequest(state: CharLoginRequestState): CharLoginAction;
|
|
51
|
+
/**
|
|
52
|
+
* The console line for a rejected login, in Mudlet's wording
|
|
53
|
+
* (`GMCPAuthenticator::handleAuthResult`). Servers doing GMCP login usually send
|
|
54
|
+
* no text of their own, so this is often the only trace of the failure.
|
|
55
|
+
*/
|
|
56
|
+
/**
|
|
57
|
+
* The console line for credentials the game never answered at all: it closed the
|
|
58
|
+
* connection instead of sending `Char.Login.Result`.
|
|
59
|
+
*
|
|
60
|
+
* Measured against Achaea (2026-08-02): a rejected `Char.Login.Credentials` gets
|
|
61
|
+
* no result, no text, no close reason — the socket simply ends. The same wrong
|
|
62
|
+
* password typed into its *text* login prints "Password incorrect. For recovery,
|
|
63
|
+
* see …" before dropping, so the silence is specific to the GMCP path. Mudlet
|
|
64
|
+
* only reports `Char.Login.Result`, so it is equally silent here; without this
|
|
65
|
+
* line a mistyped password is indistinguishable from a network failure.
|
|
66
|
+
*/
|
|
67
|
+
export declare const CHAR_LOGIN_SILENT_DROP_MESSAGE: string;
|
|
68
|
+
export declare function charLoginFailureMessage(message?: string): string;
|
|
@@ -20,7 +20,26 @@ export declare function normalizeCharsetName(raw: string): string | null;
|
|
|
20
20
|
* via `getServerEncodingsList()`. Every entry round-trips through
|
|
21
21
|
* {@link normalizeCharsetName}, so any name here is a valid `setServerEncoding`
|
|
22
22
|
* argument. ("ASCII" maps to the UTF-8 decoder, which handles it byte-for-byte.) */
|
|
23
|
+
/** What `getServerEncoding()` reports before anything has changed it. UTF-8
|
|
24
|
+
* rather than Mudlet's ASCII: the decoder handles ASCII byte-for-byte anyway,
|
|
25
|
+
* and a browser stream is far more likely to be UTF-8 than not. */
|
|
26
|
+
export declare const DEFAULT_SERVER_ENCODING = "UTF-8";
|
|
23
27
|
export declare const SUPPORTED_SERVER_ENCODINGS: readonly string[];
|
|
28
|
+
/** The {@link SUPPORTED_SERVER_ENCODINGS} entry a caller's spelling means, or
|
|
29
|
+
* null when mudix cannot decode it. Dash/space/case differences are all the
|
|
30
|
+
* same encoding — the profile XML, the wire, and Mudlet's own list disagree
|
|
31
|
+
* about which to use — so the answer is always the list's own spelling and
|
|
32
|
+
* `getServerEncoding()` reports one canonical name whatever was set. */
|
|
33
|
+
export declare function canonicalServerEncoding(raw: string): string | null;
|
|
34
|
+
/**
|
|
35
|
+
* Whether every character of `text` survives a trip to the game under
|
|
36
|
+
* `serverEncoding` — Mudlet's TEncodingHelper::canEncode, which is what decides
|
|
37
|
+
* whether a send gets the "unlikely to understand it" warning.
|
|
38
|
+
*
|
|
39
|
+
* Anything mudix cannot judge (an unknown label) is called encodable: the point
|
|
40
|
+
* is to warn about a loss that will certainly happen, not to guess.
|
|
41
|
+
*/
|
|
42
|
+
export declare function canEncodeForServer(text: string, serverEncoding: string): boolean;
|
|
24
43
|
/**
|
|
25
44
|
* Parse an `IAC SB CHARSET REQUEST ...` subnegotiation body (leading byte is
|
|
26
45
|
* the option code 42, then subcommand byte 1, then optional `[TTABLE]<ver>`
|
|
@@ -61,11 +80,14 @@ export declare class SessionCodec {
|
|
|
61
80
|
decode(byteString: string): string;
|
|
62
81
|
/** Convert a user-typed JS string (UTF-16) into the Latin-1 byte-string the
|
|
63
82
|
* socket layer expects, using the currently negotiated outgoing encoding.
|
|
64
|
-
*
|
|
65
|
-
*
|
|
66
|
-
* which
|
|
67
|
-
*
|
|
68
|
-
*
|
|
83
|
+
* UTF-8 goes through TextEncoder so multi-byte chars survive; every other
|
|
84
|
+
* encoding here is single-byte and goes through the inverted decode table,
|
|
85
|
+
* which puts the codepage's own byte on the wire. (A plain `& 0xff`
|
|
86
|
+
* truncation used to stand in for that, and was right only for the
|
|
87
|
+
* Latin-1 range — every Polish, Cyrillic, or Greek character above it went
|
|
88
|
+
* out as a byte meaning something else entirely.) A character the codepage
|
|
89
|
+
* has no byte for becomes '?', as Qt's encoder does it — and the send path
|
|
90
|
+
* warns before it comes to that. */
|
|
69
91
|
encodeOutgoing(text: string): string;
|
|
70
92
|
}
|
|
71
93
|
export interface CharsetHandlerHooks {
|
|
@@ -3,12 +3,28 @@ export interface GmcpEnvelope {
|
|
|
3
3
|
value: unknown;
|
|
4
4
|
}
|
|
5
5
|
export type TelnetOptionHandler = (data: string) => string;
|
|
6
|
-
|
|
6
|
+
/** UTF-8-encode into a Latin-1 byte-string, for MudClient.sendBytes (which
|
|
7
|
+
* writes `charCodeAt(i) & 0xff` per char). The inverse of fromByteString. */
|
|
8
|
+
export declare const toByteString: (s: string) => string;
|
|
9
|
+
export declare const createTelnetOptionParser: (onSubnegotiation: (data: string) => void, opts?: {
|
|
10
|
+
/** When true, an inbound IAC GA / IAC EOR is replaced by a newline
|
|
11
|
+
* rather than stripped — Mudlet's `mFORCE_GA_OFF` behaviour
|
|
12
|
+
* (`cTelnet::processSocketData` pushes `'\n'` in place of the marker
|
|
13
|
+
* instead of treating it as a prompt). Doing the substitution here,
|
|
14
|
+
* inside the sequence parser, keeps it positional: the newline lands
|
|
15
|
+
* exactly where the marker was, and a `\xFF\xF9` byte pair inside a
|
|
16
|
+
* subnegotiation payload is never mistaken for one. */
|
|
17
|
+
promptMarkerAsNewline?: boolean;
|
|
18
|
+
}) => TelnetOptionHandler;
|
|
7
19
|
export declare const stripTelnetSequences: (data: string, handler: TelnetOptionHandler) => string;
|
|
8
20
|
export declare const encodeGmcp: (path: string, payload: unknown) => string;
|
|
9
21
|
/** Encode a GMCP frame from a single pre-formatted body (e.g. `"Module.Sub args"`).
|
|
10
|
-
*
|
|
11
|
-
*
|
|
22
|
+
* Mudlet's `sendGMCP` semantics — the caller controls the body between IAC SB
|
|
23
|
+
* GMCP and IAC SE — except that the body is transcoded to UTF-8 rather than to
|
|
24
|
+
* the session's outgoing encoding, so it can't be used to place arbitrary raw
|
|
25
|
+
* bytes on the wire. UTF-8 is what the GMCP spec asks for, and it's also what
|
|
26
|
+
* keeps a 0xFF byte (which would need IAC-escaping inside a subnegotiation)
|
|
27
|
+
* out of the body in the first place. */
|
|
12
28
|
export declare const encodeGmcpRaw: (message: string) => string;
|
|
13
29
|
export interface GmcpStreamOptions {
|
|
14
30
|
onEnvelope: (payload: GmcpEnvelope) => void;
|
|
@@ -8,4 +8,4 @@ export { MspParser, type MspCommand, type MspKind } from "./msp";
|
|
|
8
8
|
export { MxpParser, splitMxpResultLines, type MxpLink, type MxpLineResult } from "./mxp";
|
|
9
9
|
export { parseMnesRequest, encodeMnesIs, selectMnesVars, buildNewEnvironVars, CLIENT_NAME, CLIENT_VERSION, TERMINAL_TYPE, type MnesVar, type MnesRequest, type NewEnvironState } from "./mnes";
|
|
10
10
|
export { encodeNaws } from "./naws";
|
|
11
|
-
export { SessionCodec, CharsetHandler, normalizeCharsetName, pickCharsetFromRequest, SUPPORTED_SERVER_ENCODINGS, type CharsetHandlerHooks } from "./charset";
|
|
11
|
+
export { SessionCodec, CharsetHandler, normalizeCharsetName, pickCharsetFromRequest, SUPPORTED_SERVER_ENCODINGS, DEFAULT_SERVER_ENCODING, canonicalServerEncoding, canEncodeForServer, type CharsetHandlerHooks } from "./charset";
|