@geektech/tsone 0.1.0 → 0.2.1

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-zh.md CHANGED
@@ -53,7 +53,7 @@ class App extends Component<Record<string, never>, AppState> {
53
53
  protected initState(): AppState {
54
54
  return {
55
55
  count: 0,
56
- version: '0.0.2',
56
+ version: '0.2.1',
57
57
  };
58
58
  }
59
59
 
@@ -121,16 +121,35 @@ export default defineConfig({
121
121
  ```
122
122
 
123
123
  代理也支持字符串简写,例如 `{ '/backend': 'http://localhost:4000' }`。默认值为
124
- 入口 `src/main.ts`、主机 `127.0.0.1`、端口 `52211`、空的 `server.proxy` 和
125
- 输出目录 `dist`。
124
+ 入口 `src/main.ts`、主机 `127.0.0.1`、端口 `52211`、空的 `server.proxy`、输出
125
+ 目录 `dist`,且没有额外页面。
126
+
127
+ 多页应用可在同一配置文件里把路由映射到页面入口;每个页面入口与根入口一样,
128
+ 都要通过 `export const app` 暴露带有 `renderHtmlDocument()` 的应用:
129
+
130
+ ```typescript
131
+ export default defineConfig({
132
+ entry: 'src/main.ts',
133
+ pages: {
134
+ '/about': 'src/about.ts',
135
+ '/docs/guide': 'src/guide.ts',
136
+ },
137
+ });
138
+ ```
139
+
140
+ `pages` 的键必须以 `/` 开头并支持嵌套;根路径 `/` 由 `entry` 提供。开发时每个
141
+ 页面在其路由下提供服务,`tsone build` 会为每个页面输出一个 HTML 文档
142
+ (`index.html`、`about.html`、`docs/guide.html`),资源 URL 相对各文档。
126
143
 
127
144
  ```text
128
- tsone dev [--host <host>] [--port <port>]
145
+ tsone dev [--host <host>] [--port <port>] [--no-watch]
129
146
  tsone build [--out-dir <path>]
130
147
  ```
131
148
 
132
- `dev` 只接受主机和端口覆盖,`build` 只接受输出目录覆盖;`--port 3000` 和
133
- `--port=3000` 两种形式均可。构建输出必须是项目根目录内部的安全子目录。
149
+ `dev` 接受主机、端口覆盖和 `--no-watch`;`build` 只接受输出目录覆盖;
150
+ `--port 3000` 和 `--port=3000` 两种形式均可。`tsone dev` 默认监听项目文件,
151
+ 文件变化时通过 `/__tsone/reload` 通知浏览器刷新。构建输出必须是项目根目录内部
152
+ 的安全子目录。
134
153
 
135
154
  编程式工具 API 来自 `@geektech/tsone-cli`,而不是框架主入口。该包导出
136
155
  `defineConfig`、`resolveConfig`、`startDevServer` 与 `build`。调用方负责开发
@@ -283,7 +302,7 @@ const html = app.renderHtmlDocument({
283
302
  - `effect()` / `stop()`
284
303
  - `computed()`
285
304
  - `ref()` / `isRef()` / `unref()`
286
- - `version`,当前为 `0.0.2`
305
+ - `version`,当前为 `0.2.1`
287
306
 
288
307
  ## 渲染、通信与表单
289
308
 
package/README.md CHANGED
@@ -58,7 +58,7 @@ class App extends Component<Record<string, never>, AppState> {
58
58
  protected initState(): AppState {
59
59
  return {
60
60
  count: 0,
61
- version: '0.0.2',
61
+ version: '0.2.1',
62
62
  };
63
63
  }
64
64
 
@@ -130,16 +130,38 @@ export default defineConfig({
130
130
 
131
131
  The string proxy shorthand is also supported, for example
132
132
  `{ '/backend': 'http://localhost:4000' }`. Defaults are `src/main.ts`,
133
- `127.0.0.1`, port `52211`, an empty `server.proxy`, and `dist`.
133
+ `127.0.0.1`, port `52211`, an empty `server.proxy`, `dist`, and no additional
134
+ pages.
135
+
136
+ Multi-page applications map routes to page entries in the same config file;
137
+ each page entry exposes `app` with `renderHtmlDocument()` exactly like the root
138
+ entry:
139
+
140
+ ```typescript
141
+ export default defineConfig({
142
+ entry: 'src/main.ts',
143
+ pages: {
144
+ '/about': 'src/about.ts',
145
+ '/docs/guide': 'src/guide.ts',
146
+ },
147
+ });
148
+ ```
149
+
150
+ `pages` keys must start with `/` and may nest; the root `/` is served by
151
+ `entry`. During development each page is served at its route, and `tsone build`
152
+ emits one HTML document per page (`index.html`, `about.html`,
153
+ `docs/guide.html`) with page-relative asset URLs.
134
154
 
135
155
  ```text
136
- tsone dev [--host <host>] [--port <port>]
156
+ tsone dev [--host <host>] [--port <port>] [--no-watch]
137
157
  tsone build [--out-dir <path>]
138
158
  ```
139
159
 
140
- `dev` accepts host/port overrides and `build` accepts the output-directory
141
- override; both `--port 3000` and `--port=3000` forms are valid. Build output
142
- must remain a safe child directory inside the project root.
160
+ `dev` accepts host/port overrides and `--no-watch`; `build` accepts the
161
+ output-directory override; both `--port 3000` and `--port=3000` forms are
162
+ valid. `tsone dev` watches the project by default and notifies browsers to
163
+ reload over `/__tsone/reload` when a watched file changes. Build output must
164
+ remain a safe child directory inside the project root.
143
165
 
144
166
  Programmatic tooling is imported from `@geektech/tsone-cli`, not from the
145
167
  framework root. It exports `defineConfig`, `resolveConfig`, `startDevServer`,
@@ -303,7 +325,7 @@ The main `@geektech/tsone` entry point exports:
303
325
  - `effect()` / `stop()`
304
326
  - `computed()`
305
327
  - `ref()` / `isRef()` / `unref()`
306
- - `version`, currently `0.0.2`
328
+ - `version`, currently `0.2.1`
307
329
 
308
330
  ## Rendering, Communication, and Forms
309
331
 
@@ -0,0 +1,534 @@
1
+ /**
2
+ * 零依赖最小 DOM 实现。
3
+ *
4
+ * 供 SSR(CLI 项目渲染、docs 静态构建)与测试环境使用,
5
+ * 覆盖 TSone 框架与测试实际依赖的 DOM 面(节点树、事件、CSS 选择器、
6
+ * innerHTML 序列化/解析、history/location/localStorage 等)。
7
+ * 仅面向本项目所需场景,不追求完整浏览器兼容。
8
+ */
9
+ export declare const enum DomNodeType {
10
+ ELEMENT_NODE = 1,
11
+ TEXT_NODE = 3,
12
+ COMMENT_NODE = 8,
13
+ DOCUMENT_NODE = 9,
14
+ DOCUMENT_FRAGMENT_NODE = 11
15
+ }
16
+ export declare class DOMException extends Error {
17
+ readonly code: number;
18
+ constructor(message: string, name?: string);
19
+ }
20
+ type EventListenerRecord = ((event: Event) => void) | {
21
+ handleEvent(event: Event): void;
22
+ };
23
+ interface ListenerEntry {
24
+ listener: EventListenerRecord;
25
+ capture: boolean;
26
+ once: boolean;
27
+ passive: boolean;
28
+ }
29
+ /**
30
+ * EventTarget 基类:addEventListener / removeEventListener / dispatchEvent。
31
+ */
32
+ export declare class EventTarget {
33
+ private readonly listenerMap;
34
+ addEventListener(type: string, listener: EventListenerRecord | null, options?: boolean | AddEventListenerOptions): void;
35
+ removeEventListener(type: string, listener: EventListenerRecord | null, options?: boolean | EventListenerOptions): void;
36
+ dispatchEvent(event: Event): boolean;
37
+ /** @internal 返回本节点的监听器。 */
38
+ getListeners(type: string): ListenerEntry[];
39
+ }
40
+ export declare class Event {
41
+ static readonly NONE = 0;
42
+ static readonly CAPTURING_PHASE = 1;
43
+ static readonly AT_TARGET = 2;
44
+ static readonly BUBBLING_PHASE = 3;
45
+ readonly type: string;
46
+ readonly bubbles: boolean;
47
+ readonly cancelable: boolean;
48
+ readonly composed: boolean;
49
+ target: EventTarget | null;
50
+ currentTarget: EventTarget | null;
51
+ eventPhase: number;
52
+ defaultPrevented: boolean;
53
+ readonly isTrusted = false;
54
+ readonly timeStamp: number;
55
+ cancelBubble: boolean;
56
+ /** @internal */
57
+ dispatched: boolean;
58
+ /** @internal */
59
+ private propagationStopped;
60
+ /** @internal */
61
+ private immediateStopped;
62
+ /** @internal */
63
+ private canceled;
64
+ constructor(type: string, init?: EventInit);
65
+ preventDefault(): void;
66
+ stopPropagation(): void;
67
+ stopImmediatePropagation(): void;
68
+ /** @internal */
69
+ propagationPrevented(): boolean;
70
+ /** @internal */
71
+ immediatePrevented(): boolean;
72
+ /** @internal */
73
+ wasCanceled(): boolean;
74
+ }
75
+ export declare class CustomEvent<T = unknown> extends Event {
76
+ readonly detail: T;
77
+ constructor(type: string, init?: CustomEventInit<T>);
78
+ }
79
+ export declare class MouseEvent extends Event {
80
+ readonly clientX: number;
81
+ readonly clientY: number;
82
+ readonly button: number;
83
+ readonly buttons: number;
84
+ readonly relatedTarget: unknown;
85
+ constructor(type: string, init?: MouseEventInit);
86
+ }
87
+ export declare class KeyboardEvent extends Event {
88
+ readonly key: string;
89
+ readonly code: string;
90
+ constructor(type: string, init?: KeyboardEventInit);
91
+ }
92
+ export declare class DOMTokenList implements Iterable<string> {
93
+ private readonly element;
94
+ private readonly attributeName;
95
+ constructor(element: Element, attributeName?: string);
96
+ get length(): number;
97
+ get value(): string;
98
+ set value(value: string);
99
+ item(index: number): string | null;
100
+ contains(token: string): boolean;
101
+ add(...tokens: string[]): void;
102
+ remove(...tokens: string[]): void;
103
+ toggle(token: string, force?: boolean): boolean;
104
+ replace(oldToken: string, newToken: string): boolean;
105
+ [Symbol.iterator](): Iterator<string>;
106
+ forEach(callback: (value: string, index: number, list: DOMTokenList) => void): void;
107
+ toString(): string;
108
+ private tokens;
109
+ private setTokens;
110
+ }
111
+ /**
112
+ * 创建 CSSStyleDeclaration 代理,支持任意 camelCase 属性访问与赋值。
113
+ */
114
+ export declare function createStyleDeclaration(): CSSStyleDeclaration;
115
+ /**
116
+ * 类数组节点列表:支持 .length、.item()、数值索引与迭代。
117
+ */
118
+ export declare class NodeList<T extends Node = Node> implements Iterable<T> {
119
+ /** @internal */
120
+ private readonly items;
121
+ constructor(items?: T[]);
122
+ get length(): number;
123
+ item(index: number): T | null;
124
+ [Symbol.iterator](): Iterator<T>;
125
+ forEach(callback: (value: T, index: number, list: NodeList<T>) => void): void;
126
+ entries(): IterableIterator<[number, T]>;
127
+ keys(): IterableIterator<number>;
128
+ values(): IterableIterator<T>;
129
+ toArray(): T[];
130
+ }
131
+ /**
132
+ * Node 基类:节点树、父子关系、文本内容。
133
+ */
134
+ export declare class Node extends EventTarget {
135
+ static readonly ELEMENT_NODE = DomNodeType.ELEMENT_NODE;
136
+ static readonly TEXT_NODE = DomNodeType.TEXT_NODE;
137
+ static readonly COMMENT_NODE = DomNodeType.COMMENT_NODE;
138
+ static readonly DOCUMENT_NODE = DomNodeType.DOCUMENT_NODE;
139
+ static readonly DOCUMENT_FRAGMENT_NODE = DomNodeType.DOCUMENT_FRAGMENT_NODE;
140
+ readonly nodeType: number;
141
+ readonly nodeName: string;
142
+ parentNode: Node | null;
143
+ ownerDocument: Document | null;
144
+ /** @internal */
145
+ childList: Node[];
146
+ constructor(nodeType: number, nodeName: string);
147
+ get parentElement(): Element | null;
148
+ get childNodes(): NodeList<Node>;
149
+ get firstChild(): Node | null;
150
+ get lastChild(): Node | null;
151
+ get nextSibling(): Node | null;
152
+ get previousSibling(): Node | null;
153
+ get textContent(): string;
154
+ set textContent(value: string);
155
+ hasChildNodes(): boolean;
156
+ appendChild<T extends Node>(node: T): T;
157
+ insertBefore<T extends Node>(node: T, reference: Node | null): T;
158
+ removeChild<T extends Node>(node: T): T;
159
+ replaceChild<T extends Node>(newChild: T, oldChild: Node): T;
160
+ replaceChildren(...nodes: Node[]): void;
161
+ contains(node: Node | null): boolean;
162
+ remove(): void;
163
+ cloneNode(deep?: boolean): Node;
164
+ /** @internal */
165
+ protected createClone(): Node;
166
+ getRootNode(): Node;
167
+ isConnected(): boolean;
168
+ }
169
+ /**
170
+ * Element:标签节点。
171
+ */
172
+ export declare class Element extends Node {
173
+ readonly namespaceURI: string | null;
174
+ /** @internal */
175
+ private readonly attributeList;
176
+ /** @internal */
177
+ private styleValue;
178
+ /** @internal */
179
+ private classListValue;
180
+ /** @internal */
181
+ private datasetProxy;
182
+ constructor(tagName: string, namespaceURI?: string | null);
183
+ get tagName(): string;
184
+ get localName(): string;
185
+ get id(): string;
186
+ set id(value: string);
187
+ get className(): string;
188
+ set className(value: string);
189
+ get classList(): DOMTokenList;
190
+ get style(): CSSStyleDeclaration;
191
+ get dataset(): Record<string, string>;
192
+ get children(): NodeList<Element>;
193
+ get firstElementChild(): Element | null;
194
+ get lastElementChild(): Element | null;
195
+ get childElementCount(): number;
196
+ get attributes(): NamedNodeMap;
197
+ getAttribute(name: string): string | null;
198
+ getAttributeNames(): string[];
199
+ setAttribute(name: string, value: unknown): void;
200
+ removeAttribute(name: string): void;
201
+ hasAttribute(name: string): boolean;
202
+ toggleAttribute(name: string, force?: boolean): boolean;
203
+ hasAttributes(): boolean;
204
+ get innerHTML(): string;
205
+ set innerHTML(value: string);
206
+ get outerHTML(): string;
207
+ get value(): string;
208
+ set value(value: string);
209
+ querySelector(selector: string): Element | null;
210
+ querySelectorAll(selector: string): NodeList<Element>;
211
+ getElementsByTagName(tagName: string): NodeList<Element>;
212
+ matches(selector: string): boolean;
213
+ closest(selector: string): Element | null;
214
+ getBoundingClientRect(): DOMRect;
215
+ scrollIntoView(): void;
216
+ focus(): void;
217
+ blur(): void;
218
+ click(): void;
219
+ append(...nodes: (Node | string)[]): void;
220
+ prepend(...nodes: (Node | string)[]): void;
221
+ before(...nodes: (Node | string)[]): void;
222
+ after(...nodes: (Node | string)[]): void;
223
+ replaceWith(...nodes: (Node | string)[]): void;
224
+ setAttributeNS(_namespace: string, name: string, value: unknown): void;
225
+ removeAttributeNS(_namespace: string, name: string): void;
226
+ hasAttributeNS(_namespace: string, name: string): boolean;
227
+ getAttributeNS(_namespace: string, name: string): string | null;
228
+ /** @internal */
229
+ findAttribute(name: string): {
230
+ name: string;
231
+ value: string;
232
+ } | undefined;
233
+ /** @internal */
234
+ attributeEntries(): Array<{
235
+ name: string;
236
+ value: string;
237
+ }>;
238
+ /** @internal 供序列化读取内联样式。 */
239
+ inlineStyleText(): string;
240
+ /** @internal */
241
+ protected createClone(): Node;
242
+ }
243
+ export declare class HTMLElement extends Element {
244
+ constructor(tagName: string);
245
+ }
246
+ export declare class NamedNodeMap implements Iterable<{
247
+ name: string;
248
+ value: string;
249
+ }> {
250
+ private readonly element;
251
+ constructor(element: Element);
252
+ get length(): number;
253
+ item(index: number): {
254
+ name: string;
255
+ value: string;
256
+ } | null;
257
+ getNamedItem(name: string): {
258
+ name: string;
259
+ value: string;
260
+ } | null;
261
+ setNamedItem(attr: {
262
+ name: string;
263
+ value: string;
264
+ }): void;
265
+ removeNamedItem(name: string): void;
266
+ [Symbol.iterator](): Iterator<{
267
+ name: string;
268
+ value: string;
269
+ }>;
270
+ }
271
+ export declare class HTMLOptionElement extends HTMLElement {
272
+ /** @internal */
273
+ private selectedValue;
274
+ constructor(tagName?: string);
275
+ get value(): string;
276
+ set value(value: string);
277
+ get text(): string;
278
+ get label(): string;
279
+ get selected(): boolean;
280
+ set selected(value: boolean);
281
+ /** @internal */
282
+ setSelectedRaw(value: boolean): void;
283
+ /** @internal */
284
+ hasSelectedValue(): boolean;
285
+ }
286
+ export declare class HTMLSelectElement extends HTMLElement {
287
+ constructor(tagName?: string);
288
+ get multiple(): boolean;
289
+ set multiple(value: boolean);
290
+ get options(): HTMLOptionsCollection;
291
+ get selectedOptions(): NodeList<HTMLOptionElement>;
292
+ get selectedIndex(): number;
293
+ set selectedIndex(index: number);
294
+ get value(): string;
295
+ set value(value: string);
296
+ add(option: HTMLOptionElement): void;
297
+ removeOption(index: number): void;
298
+ }
299
+ export declare class HTMLOptionsCollection implements Iterable<HTMLOptionElement> {
300
+ private readonly items;
301
+ constructor(items: HTMLOptionElement[]);
302
+ get length(): number;
303
+ item(index: number): HTMLOptionElement | null;
304
+ get value(): string;
305
+ get selectedIndex(): number;
306
+ toArray(): HTMLOptionElement[];
307
+ [Symbol.iterator](): Iterator<HTMLOptionElement>;
308
+ }
309
+ export declare class HTMLInputElement extends HTMLElement {
310
+ /** @internal */
311
+ private inputValue;
312
+ /** @internal */
313
+ private checkedValue;
314
+ constructor(tagName?: string);
315
+ get type(): string;
316
+ set type(value: string);
317
+ get name(): string;
318
+ set name(value: string);
319
+ get value(): string;
320
+ set value(value: string);
321
+ get defaultValue(): string;
322
+ get checked(): boolean;
323
+ set checked(value: boolean);
324
+ get disabled(): boolean;
325
+ set disabled(value: boolean);
326
+ /** @internal */
327
+ protected createClone(): Node;
328
+ }
329
+ export declare class HTMLTextAreaElement extends HTMLElement {
330
+ /** @internal */
331
+ private textareaValue;
332
+ constructor(tagName?: string);
333
+ get value(): string;
334
+ set value(value: string);
335
+ }
336
+ export declare class HTMLButtonElement extends HTMLElement {
337
+ constructor(tagName?: string);
338
+ get type(): string;
339
+ }
340
+ export declare class HTMLStyleElement extends HTMLElement {
341
+ constructor(tagName?: string);
342
+ }
343
+ export declare class HTMLAnchorElement extends HTMLElement {
344
+ constructor(tagName?: string);
345
+ get href(): string;
346
+ set href(value: string);
347
+ }
348
+ export declare class Text extends Node {
349
+ data: string;
350
+ constructor(data?: string);
351
+ get nodeValue(): string;
352
+ set nodeValue(value: string);
353
+ get textContent(): string;
354
+ set textContent(value: string);
355
+ get wholeText(): string;
356
+ /** @internal */
357
+ protected createClone(): Node;
358
+ }
359
+ export declare class Comment extends Node {
360
+ data: string;
361
+ constructor(data?: string);
362
+ get nodeValue(): string;
363
+ set nodeValue(value: string);
364
+ /** @internal */
365
+ protected createClone(): Node;
366
+ }
367
+ export declare class DocumentFragment extends Node {
368
+ constructor();
369
+ }
370
+ export declare class Document extends Node {
371
+ readonly defaultView: DomWindow | null;
372
+ constructor();
373
+ createElement(tagName: string): HTMLElement;
374
+ createElementNS(namespaceURI: string, tagName: string): HTMLElement;
375
+ createTextNode(data: string): Text;
376
+ createComment(data: string): Comment;
377
+ createDocumentFragment(): DocumentFragment;
378
+ createEvent(type: string): Event;
379
+ get documentElement(): HTMLElement;
380
+ get head(): HTMLElement;
381
+ get body(): HTMLElement;
382
+ get title(): string;
383
+ set title(value: string);
384
+ querySelector(selector: string): Element | null;
385
+ querySelectorAll(selector: string): NodeList<Element>;
386
+ getElementById(id: string): Element | null;
387
+ getElementsByTagName(tagName: string): NodeList<Element>;
388
+ /** @internal */
389
+ protected createClone(): Node;
390
+ private ensureDocumentChild;
391
+ }
392
+ /**
393
+ * History / Location / Storage 等浏览器环境对象。
394
+ */
395
+ export declare class Location {
396
+ /** @internal */
397
+ private url;
398
+ constructor(url: string);
399
+ get href(): string;
400
+ set href(value: string);
401
+ get origin(): string;
402
+ get protocol(): string;
403
+ get host(): string;
404
+ get hostname(): string;
405
+ get port(): string;
406
+ get pathname(): string;
407
+ set pathname(value: string);
408
+ get search(): string;
409
+ set search(value: string);
410
+ get hash(): string;
411
+ set hash(value: string);
412
+ get username(): string;
413
+ get password(): string;
414
+ assign(value: string): void;
415
+ replace(value: string): void;
416
+ reload(): void;
417
+ toString(): string;
418
+ /** @internal */
419
+ getHashPath(): string;
420
+ /** @internal */
421
+ getHrefWithoutHash(): string;
422
+ }
423
+ export declare class History {
424
+ /** @internal */
425
+ private readonly windowRef;
426
+ /** @internal */
427
+ private entries;
428
+ /** @internal */
429
+ private index;
430
+ /** @internal */
431
+ scrollRestoration: 'auto' | 'manual';
432
+ constructor(windowRef: DomWindow);
433
+ get length(): number;
434
+ get state(): unknown;
435
+ pushState(state: unknown, _unusedTitle: string, url?: string): void;
436
+ replaceState(state: unknown, _unusedTitle: string, url?: string): void;
437
+ back(): void;
438
+ forward(): void;
439
+ go(delta?: number): void;
440
+ }
441
+ export declare class Storage {
442
+ private readonly store;
443
+ get length(): number;
444
+ key(index: number): string | null;
445
+ getItem(key: string): string | null;
446
+ setItem(key: string, value: string): void;
447
+ removeItem(key: string): void;
448
+ clear(): void;
449
+ }
450
+ export declare class Navigator {
451
+ readonly userAgent = "TSone/0.2.1";
452
+ readonly platform = "TSone";
453
+ readonly language = "zh-CN";
454
+ readonly languages: string[];
455
+ readonly onLine = true;
456
+ readonly maxTouchPoints = 0;
457
+ }
458
+ export interface MediaQueryList {
459
+ readonly media: string;
460
+ readonly matches: boolean;
461
+ onchange: ((event: Event) => void) | null;
462
+ addEventListener(type: string, listener: EventListenerRecord): void;
463
+ removeEventListener(type: string, listener: EventListenerRecord): void;
464
+ addListener(listener: EventListenerRecord): void;
465
+ removeListener(listener: EventListenerRecord): void;
466
+ dispatchEvent(event: Event): boolean;
467
+ }
468
+ export declare function createMatchMedia(_windowRef: DomWindow, query: string): MediaQueryList;
469
+ export declare class ResizeObserver {
470
+ observe(): void;
471
+ unobserve(): void;
472
+ disconnect(): void;
473
+ }
474
+ export declare const DOM_GLOBAL_KEYS: readonly string[];
475
+ /**
476
+ * DomWindow:模拟的浏览器 window 环境。
477
+ */
478
+ export declare class DomWindow extends EventTarget {
479
+ readonly window: DomWindow;
480
+ readonly document: Document;
481
+ readonly location: Location;
482
+ readonly history: History;
483
+ readonly localStorage: Storage;
484
+ readonly navigator: Navigator;
485
+ readonly Node: typeof Node;
486
+ readonly Text: typeof Text;
487
+ readonly Comment: typeof Comment;
488
+ readonly Element: typeof Element;
489
+ readonly HTMLElement: typeof HTMLElement;
490
+ readonly HTMLInputElement: typeof HTMLInputElement;
491
+ readonly HTMLTextAreaElement: typeof HTMLTextAreaElement;
492
+ readonly HTMLSelectElement: typeof HTMLSelectElement;
493
+ readonly HTMLButtonElement: typeof HTMLButtonElement;
494
+ readonly HTMLOptionElement: typeof HTMLOptionElement;
495
+ readonly HTMLStyleElement: typeof HTMLStyleElement;
496
+ readonly HTMLAnchorElement: typeof HTMLAnchorElement;
497
+ readonly DocumentFragment: typeof DocumentFragment;
498
+ readonly Document: typeof Document;
499
+ readonly Event: typeof Event;
500
+ readonly MouseEvent: typeof MouseEvent;
501
+ readonly KeyboardEvent: typeof KeyboardEvent;
502
+ readonly CustomEvent: typeof CustomEvent;
503
+ readonly EventTarget: typeof EventTarget;
504
+ readonly DOMException: typeof DOMException;
505
+ readonly NodeList: typeof NodeList;
506
+ constructor(options?: {
507
+ url?: string;
508
+ });
509
+ matchMedia(query: string): MediaQueryList;
510
+ getComputedStyle(element: Element): CSSStyleDeclaration;
511
+ requestAnimationFrame(callback: FrameRequestCallback): number;
512
+ cancelAnimationFrame(handle: number): void;
513
+ /** @internal */
514
+ setLocationUrl(url: string): void;
515
+ /** @internal 安装到目标对象上的全局属性名。 */
516
+ installKeys(): string[];
517
+ }
518
+ export interface DomWindowOptions {
519
+ url?: string;
520
+ }
521
+ /**
522
+ * 创建隔离的 DOM window 环境。
523
+ */
524
+ export declare function createDomWindow(options?: DomWindowOptions): DomWindow;
525
+ /**
526
+ * 将 DOM window 的全局属性安装到目标对象(默认 globalThis),
527
+ * 返回可恢复旧值的函数。
528
+ */
529
+ export declare function installDomGlobals(windowRef: DomWindow, target?: Record<string, unknown>): () => void;
530
+ /**
531
+ * 解析 HTML 片段为节点列表(innerHTML setter 用)。
532
+ */
533
+ export declare function parseHtmlFragment(source: string, documentRef: Document | null): Node[];
534
+ export {};