@jboltai/tokui 0.1.6 → 0.1.8

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@jboltai/tokui",
3
- "version": "0.1.6",
3
+ "version": "0.1.8",
4
4
  "description": "TokUI — Zero-dependency streaming UI description & rendering framework for AI chat. Describe UI with a tiny DSL, stream over SSE, render to real DOM incrementally.",
5
5
  "keywords": [
6
6
  "tokui",
@@ -73,6 +73,7 @@
73
73
  "provenance": true
74
74
  },
75
75
  "devDependencies": {
76
+ "@playwright/test": "^1.61.1",
76
77
  "c8": "^10.1.3",
77
78
  "typescript": "^6.0.3",
78
79
  "vite": "^8.0.16",
@@ -81,6 +82,7 @@
81
82
  "scripts": {
82
83
  "test": "npm run test:all",
83
84
  "test:all": "for f in tests/test-*.js; do node \"$f\" || exit 1; done",
85
+ "test:e2e": "playwright test",
84
86
  "test:core": "node tests/test-event-bus.js && node tests/test-theme.js && node tests/test-renderer.js",
85
87
  "test:parser": "node tests/test-parser.js",
86
88
  "test:builder": "node tests/test-builder.js",
package/src/index.d.ts CHANGED
@@ -10,9 +10,24 @@
10
10
  */
11
11
  export type TokUIHandlerFn = (data: any, event: Event, element: HTMLElement) => void;
12
12
 
13
+ /**
14
+ * 组件交互事件 payload(onEvent('component', evt) 的第二参)
15
+ * DSL `on:"事件:处理器"` 之外的统一事件出口:所有接入上报的组件交互都会发到这里。
16
+ */
17
+ export interface TokUIComponentEvent {
18
+ /** 组件类型,如 'input' / 'tabs' / 'dialog' / 'tool-call' */
19
+ type: string;
20
+ /** 组件 id 属性(无则 null) */
21
+ id: string | null;
22
+ /** 事件名,如 'change' / 'close' / 'stop' / 'approval' */
23
+ event: string;
24
+ /** 事件上下文,如 { value } / { index, title } / { approved, id, name } */
25
+ detail: any;
26
+ }
27
+
13
28
  /**
14
29
  * onEvent 回调签名
15
- * @param eventName - 事件名,如 'streamEnd'
30
+ * @param eventName - 事件名:'streamEnd'(流结束)/ 'component'(组件交互,data 为 TokUIComponentEvent)
16
31
  * @param data - 事件数据
17
32
  */
18
33
  export type TokUIEventCallback = (eventName: string, data: any) => void;
@@ -34,8 +49,10 @@ export interface TokUIOptions {
34
49
  locale?: string;
35
50
  /** 是否启用流式渲染模式,默认 true */
36
51
  streaming?: boolean;
37
- /** 事件回调,如接收到 ('streamEnd', {}) */
52
+ /** 事件回调:('streamEnd', {}) 流结束;('component', TokUIComponentEvent) 组件交互统一出口 */
38
53
  onEvent?: TokUIEventCallback | null;
54
+ /** 组件交互事件过滤器:返回 false 丢弃该事件(onEvent 降噪用,如只看某类组件) */
55
+ eventFilter?: ((evt: TokUIComponentEvent) => boolean) | null;
39
56
  }
40
57
 
41
58
  /**
@@ -256,6 +256,16 @@ class TokUIBuilder {
256
256
  /** 容器内原始文本(用于 textarea/md/code 等容器组件) */
257
257
  text(content) { this.chunks.push(String(content)); return this; }
258
258
 
259
+ // ========== 行内格式组件(p/list 等容器内的文本修饰) ==========
260
+
261
+ /** 粗体 */ b(content) { return this._selfClosing('b', content); }
262
+ /** 粗体(strong 语义) */ strong(content) { return this._selfClosing('strong', content); }
263
+ /** 斜体 */ em(content) { return this._selfClosing('em', content); }
264
+ /** 高亮标记 */ mark(content) { return this._selfClosing('mark', content); }
265
+ /** 删除线 */ del(content) { return this._selfClosing('del', content); }
266
+ /** 下标 */ sub(content) { return this._selfClosing('sub', content); }
267
+ /** 上标 */ sup(content) { return this._selfClosing('sup', content); }
268
+
259
269
  // ========== 布局组件 ==========
260
270
 
261
271
  /** 卡片(容器模式:需 .end() 关闭) */
@@ -598,8 +608,8 @@ class TokUIBuilder {
598
608
  /** 计划步骤(自闭合或容器) */
599
609
  planStep(attrs) { return this._selfClosing('plan-step', null, attrs); }
600
610
 
601
- /** Agent 状态卡片(自闭合或容器) */
602
- agent(attrs) { return attrs && (attrs.status || attrs.name) && !attrs._container ? this._selfClosing('agent', null, attrs) : this._open('agent', attrs); }
611
+ /** Agent 状态卡片(自闭合;agent 组件纯 attr 驱动,无 children 语义) */
612
+ agent(attrs) { return this._selfClosing('agent', null, attrs); }
603
613
 
604
614
  /** 文件树(容器) */
605
615
  fileTree(attrs) { return this._open('file-tree', attrs); }