@netless/window-manager 0.4.26 → 0.4.27-canary.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/dist/App/AppContext.d.ts +2 -1
- package/dist/App/AppProxy.d.ts +6 -3
- package/dist/AppListener.d.ts +1 -0
- package/dist/AppManager.d.ts +2 -0
- package/dist/InternalEmitter.d.ts +5 -1
- package/dist/Page/PageController.d.ts +5 -0
- package/dist/Page/index.d.ts +2 -0
- package/dist/Utils/Common.d.ts +2 -1
- package/dist/Utils/error.d.ts +3 -0
- package/dist/View/MainView.d.ts +1 -0
- package/dist/constants.d.ts +1 -0
- package/dist/index.cjs.js +12 -12
- package/dist/index.cjs.js.map +1 -1
- package/dist/index.d.ts +1 -0
- package/dist/index.es.js +210 -53
- package/dist/index.es.js.map +1 -1
- package/dist/index.umd.js +12 -12
- package/dist/index.umd.js.map +1 -1
- package/dist/typings.d.ts +1 -0
- package/docs/advanced.md +17 -0
- package/docs/api.md +8 -0
- package/docs/app-context.md +149 -100
- package/package.json +1 -1
- package/src/App/AppContext.ts +20 -11
- package/src/App/AppProxy.ts +55 -4
- package/src/App/Storage/index.ts +14 -8
- package/src/AppListener.ts +22 -0
- package/src/AppManager.ts +57 -24
- package/src/InternalEmitter.ts +4 -1
- package/src/Page/PageController.ts +6 -0
- package/src/Page/index.ts +18 -0
- package/src/PageState.ts +2 -1
- package/src/Utils/Common.ts +14 -2
- package/src/Utils/RoomHacker.ts +2 -2
- package/src/Utils/error.ts +4 -0
- package/src/View/MainView.ts +7 -3
- package/src/constants.ts +1 -0
- package/src/index.ts +16 -0
- package/src/typings.ts +1 -0
package/dist/typings.d.ts
CHANGED
@@ -74,3 +74,4 @@ export type { ReadonlyTeleBox, TeleBoxRect };
|
|
74
74
|
export type { SceneState, SceneDefinition, View, AnimationMode, Displayer, Room, Player };
|
75
75
|
export type { Storage, StorageStateChangedEvent, StorageStateChangedListener } from "./App/Storage";
|
76
76
|
export * from "./Page";
|
77
|
+
export * from "./Utils/error";
|
package/docs/advanced.md
CHANGED
@@ -6,6 +6,7 @@
|
|
6
6
|
- [判断是否打开某种 APP](#has-kind)
|
7
7
|
- [页面控制器](#page-control)
|
8
8
|
- [视角](#view-mode)
|
9
|
+
- [插入图片到当前app](#insert-image-to-app)
|
9
10
|
|
10
11
|
|
11
12
|
<h3 id="redo-undo">撤销重做</h3>
|
@@ -109,3 +110,19 @@ manager.addPage()
|
|
109
110
|
同时其他为 `broadcaster` 模式的人也会影响我的视角
|
110
111
|
|
111
112
|
在 `isWritable` 为 `false` 时只会跟随其他 `broadcaster` 的视角
|
113
|
+
|
114
|
+
<br>
|
115
|
+
|
116
|
+
<h3 id="insert-image-to-app">插入图片到当前 app</h3>
|
117
|
+
|
118
|
+
```ts
|
119
|
+
// 判断当前是否为最大化
|
120
|
+
if (manager.boxState === "maximized") {
|
121
|
+
// `focused` 的值的会根据当前 focus 的 app 不同而变化
|
122
|
+
const app = manager.queryOne(manager.focused)
|
123
|
+
// 有 view 的 app 才可以插入图片, 像是 视频,音频之类的 app 是没有 view 的
|
124
|
+
if (app.view) {
|
125
|
+
app.view.insertImage()
|
126
|
+
}
|
127
|
+
}
|
128
|
+
```
|
package/docs/api.md
CHANGED
@@ -214,6 +214,14 @@ manager.addPage({ after: true }) // 在当前页后添加一页
|
|
214
214
|
manager.addPage({ scene: { name: "page2" } }) // 传入 page 信息
|
215
215
|
```
|
216
216
|
|
217
|
+
<h3 id="removePage">removePage</h3>
|
218
|
+
|
219
|
+
> 移除一页
|
220
|
+
|
221
|
+
```ts
|
222
|
+
const success = await manager.removePage(1)
|
223
|
+
```
|
224
|
+
|
217
225
|
<h3 id="refresh">refresh</h3>
|
218
226
|
|
219
227
|
> 刷新 `manager` 的内部状态, 用于从其他房间 `copy` `attributes`
|
package/docs/app-context.md
CHANGED
@@ -1,156 +1,205 @@
|
|
1
1
|
## AppContext
|
2
2
|
|
3
|
-
-
|
4
|
-
- [
|
3
|
+
- [api](#api)
|
4
|
+
- [view](#view)
|
5
|
+
- [page](#page)
|
6
|
+
- [storage](#storage)
|
7
|
+
- [events](#events)
|
5
8
|
|
6
9
|
<h2 id="api">API</h2>
|
7
10
|
|
8
|
-
|
11
|
+
- **context.appId**
|
9
12
|
|
10
|
-
插入 `app` 时生成的唯一 ID
|
13
|
+
插入 `app` 时生成的唯一 ID
|
11
14
|
|
12
|
-
```ts
|
13
|
-
const appId = context.appId
|
14
|
-
```
|
15
|
+
```ts
|
16
|
+
const appId = context.appId;
|
17
|
+
```
|
15
18
|
|
16
|
-
|
19
|
+
- **context.getDisplayer()**
|
17
20
|
|
18
|
-
在默认情况下 `Displayer` 为白板的 `room` 实例
|
21
|
+
在默认情况下 `Displayer` 为白板的 `room` 实例
|
19
22
|
|
20
|
-
回放时则为 `Player` 实例
|
23
|
+
回放时则为 `Player` 实例
|
21
24
|
|
22
|
-
```ts
|
23
|
-
const displayer = context.getDisplayer()
|
25
|
+
```ts
|
26
|
+
const displayer = context.getDisplayer();
|
24
27
|
|
25
|
-
assert(displayer, room) // 互动房间
|
26
|
-
assert(displayer, player) // 回放房间
|
27
|
-
```
|
28
|
+
assert(displayer, room); // 互动房间
|
29
|
+
assert(displayer, player); // 回放房间
|
30
|
+
```
|
28
31
|
|
29
|
-
### getScenes
|
30
32
|
|
31
|
-
|
33
|
+
- **context.getIsWritable()**
|
32
34
|
|
33
|
-
|
34
|
-
const scenes = context.getScenes()
|
35
|
-
```
|
35
|
+
获取当前状态是否可写
|
36
36
|
|
37
|
-
|
37
|
+
```ts
|
38
|
+
// isWritable === (room.isWritable && box.readonly)
|
39
|
+
const isWritable = context.getIsWritable();
|
40
|
+
```
|
38
41
|
|
39
|
-
|
42
|
+
- **context.getBox()**
|
40
43
|
|
41
|
-
|
42
|
-
const view = context.getView()
|
43
|
-
```
|
44
|
+
获取当前 app 的 box
|
44
45
|
|
45
|
-
|
46
|
+
```ts
|
47
|
+
const box = context.getBox();
|
46
48
|
|
47
|
-
|
49
|
+
box.$content; // box 的 main element
|
50
|
+
box.$footer;
|
51
|
+
```
|
48
52
|
|
49
|
-
|
50
|
-
// isWritable === (room.isWritable && box.readonly)
|
51
|
-
const isWritable = context.getIsWritable()
|
52
|
-
```
|
53
|
+
<h3 id="view">View</h3>
|
53
54
|
|
54
|
-
|
55
|
+
`view` 可以理解为一块白板,可以从 `context` 中拿到这个实例并挂载到 `Dom` 中
|
55
56
|
|
56
|
-
|
57
|
+
- **context.getView()**
|
57
58
|
|
58
|
-
|
59
|
-
const box = context.getBox()
|
59
|
+
获取 `view` 实例
|
60
60
|
|
61
|
-
|
62
|
-
|
63
|
-
```
|
61
|
+
```ts
|
62
|
+
const view = context.getView();
|
63
|
+
```
|
64
64
|
|
65
|
-
|
65
|
+
- **context.mountView()**
|
66
66
|
|
67
|
-
|
67
|
+
挂载 view 到指定 dom
|
68
68
|
|
69
|
-
```ts
|
70
|
-
context.
|
71
|
-
```
|
69
|
+
```ts
|
70
|
+
context.mountView(element);
|
71
|
+
```
|
72
72
|
|
73
|
-
|
73
|
+
- **context.getScenes()**
|
74
74
|
|
75
|
-
|
75
|
+
`scenes` 在 `addApp` 时传入 `scenePath` 会由 `WindowManager` 创建
|
76
76
|
|
77
|
-
```ts
|
78
|
-
context.
|
79
|
-
```
|
77
|
+
```ts
|
78
|
+
const scenes = context.getScenes();
|
79
|
+
```
|
80
80
|
|
81
|
-
|
81
|
+
- **context.setScenePath()**
|
82
82
|
|
83
|
-
|
84
|
-
context.addPage()
|
85
|
-
```
|
83
|
+
切换当前 `view` 到指定的 `scenePath`
|
86
84
|
|
87
|
-
|
85
|
+
```ts
|
86
|
+
context.setScenePath("/page/2");
|
87
|
+
```
|
88
88
|
|
89
|
-
```ts
|
90
|
-
context.nextPage()
|
91
|
-
```
|
92
89
|
|
93
|
-
|
90
|
+
<h3 id="page">Page</h3>
|
94
91
|
|
95
|
-
|
96
|
-
context.prevPage()
|
97
|
-
```
|
92
|
+
`Page` 是封装后 `scenes` 的一些概念
|
98
93
|
|
99
|
-
|
94
|
+
- **context.addPage()**
|
100
95
|
|
101
|
-
|
102
|
-
context.pageState
|
103
|
-
```
|
96
|
+
添加一页至 `view`
|
104
97
|
|
98
|
+
```ts
|
99
|
+
context.addPage() // 默认在最后添加一页
|
100
|
+
context.addPage({ after: true }) // 在当前页后添加一页
|
101
|
+
context.addPage({ scene: { name: "page2" } }) // 传入 page 信息
|
102
|
+
```
|
105
103
|
|
106
|
-
|
104
|
+
- **context.nextPage()**
|
105
|
+
|
106
|
+
上一页
|
107
|
+
|
108
|
+
```ts
|
109
|
+
context.nextPage();
|
110
|
+
```
|
111
|
+
|
112
|
+
- **context.prevPage()**
|
113
|
+
|
114
|
+
下一页
|
115
|
+
|
116
|
+
```ts
|
117
|
+
context.prevPage();
|
118
|
+
```
|
119
|
+
|
120
|
+
- **context.pageState**
|
121
|
+
|
122
|
+
获取当前所在的 `index` 和一共有多少页
|
123
|
+
|
124
|
+
```ts
|
125
|
+
context.pageState;
|
126
|
+
// {
|
127
|
+
// index: number,
|
128
|
+
// length: number,
|
129
|
+
// }
|
130
|
+
```
|
131
|
+
|
132
|
+
<h3 id="storage">storage</h3>
|
133
|
+
|
134
|
+
存储和同步状态,以及发送事件的一系列集合
|
107
135
|
|
108
|
-
|
136
|
+
- **context.storage**
|
137
|
+
|
138
|
+
默认创建的 storage 实例
|
139
|
+
|
140
|
+
```ts
|
141
|
+
context.storage
|
142
|
+
```
|
143
|
+
|
144
|
+
- **createStorage()**
|
145
|
+
|
146
|
+
同时你也可以创建多个 `storage` 实例
|
147
|
+
|
148
|
+
```ts
|
149
|
+
const defaultState = { count: 0 } // 可选
|
150
|
+
const storage = context.createStorage("store1", defaultState);
|
151
|
+
```
|
152
|
+
|
153
|
+
|
154
|
+
|
155
|
+
|
156
|
+
<h2 id="events">events</h2>
|
109
157
|
|
110
|
-
|
158
|
+
- **destroy**
|
111
159
|
|
112
|
-
|
113
|
-
context.emitter.on("destroy", () => {
|
114
|
-
// release your listeners
|
115
|
-
})
|
116
|
-
```
|
160
|
+
app 被关闭时发送
|
117
161
|
|
118
|
-
|
162
|
+
```ts
|
163
|
+
context.emitter.on("destroy", () => {
|
164
|
+
// release your listeners
|
165
|
+
});
|
166
|
+
```
|
119
167
|
|
120
|
-
|
168
|
+
- **writableChange**
|
121
169
|
|
122
|
-
|
123
|
-
context.emitter.on("writableChange", isWritable => {
|
124
|
-
//
|
125
|
-
})
|
126
|
-
```
|
170
|
+
白板可写状态切换时触发
|
127
171
|
|
128
|
-
|
172
|
+
```ts
|
173
|
+
context.emitter.on("writableChange", isWritable => {
|
174
|
+
//
|
175
|
+
});
|
176
|
+
```
|
129
177
|
|
130
|
-
|
178
|
+
- **focus**
|
131
179
|
|
132
|
-
|
133
|
-
context.emitter.on("focus", focus => {
|
134
|
-
//
|
135
|
-
})
|
136
|
-
```
|
180
|
+
当前 app 获得焦点或者失去焦点时触发
|
137
181
|
|
182
|
+
```ts
|
183
|
+
context.emitter.on("focus", focus => {
|
184
|
+
//
|
185
|
+
});
|
186
|
+
```
|
138
187
|
|
139
|
-
|
188
|
+
- **pageStateChange**
|
140
189
|
|
141
|
-
|
190
|
+
`PageState`
|
142
191
|
|
143
|
-
```ts
|
144
|
-
type PateState {
|
145
|
-
|
146
|
-
|
147
|
-
}
|
148
|
-
```
|
192
|
+
```ts
|
193
|
+
type PateState {
|
194
|
+
index: number;
|
195
|
+
length: number;
|
196
|
+
}
|
197
|
+
```
|
149
198
|
|
150
|
-
当前页数和总页数变化时触发
|
199
|
+
当前页数和总页数变化时触发
|
151
200
|
|
152
|
-
```ts
|
153
|
-
context.emitter.on("pageStateChange", pageState => {
|
154
|
-
|
155
|
-
})
|
156
|
-
```
|
201
|
+
```ts
|
202
|
+
context.emitter.on("pageStateChange", pageState => {
|
203
|
+
// { index: 0, length: 1 }
|
204
|
+
});
|
205
|
+
```
|
package/package.json
CHANGED
package/src/App/AppContext.ts
CHANGED
@@ -82,6 +82,17 @@ export class AppContext<TAttributes = any, TMagixEventPayloads = any, TAppOption
|
|
82
82
|
return this.appProxy.view;
|
83
83
|
};
|
84
84
|
|
85
|
+
public mountView = (dom: HTMLElement): void => {
|
86
|
+
const view = this.getView();
|
87
|
+
if (view) {
|
88
|
+
view.divElement = dom as HTMLDivElement;
|
89
|
+
setTimeout(() => {
|
90
|
+
// 渲染需要时间,延迟 refresh
|
91
|
+
this.getRoom()?.refreshViewSize();
|
92
|
+
}, 1000);
|
93
|
+
}
|
94
|
+
};
|
95
|
+
|
85
96
|
public getInitScenePath = () => {
|
86
97
|
return this.manager.getAppInitPath(this.appId);
|
87
98
|
};
|
@@ -124,17 +135,6 @@ export class AppContext<TAttributes = any, TMagixEventPayloads = any, TAppOption
|
|
124
135
|
this.getRoom()?.setScenePath(scenePath);
|
125
136
|
};
|
126
137
|
|
127
|
-
public mountView = (dom: HTMLElement): void => {
|
128
|
-
const view = this.getView();
|
129
|
-
if (view) {
|
130
|
-
view.divElement = dom as HTMLDivElement;
|
131
|
-
setTimeout(() => {
|
132
|
-
// 渲染需要时间,延迟 refresh
|
133
|
-
this.getRoom()?.refreshViewSize();
|
134
|
-
}, 1000);
|
135
|
-
}
|
136
|
-
};
|
137
|
-
|
138
138
|
/** Get the local App options. */
|
139
139
|
public getAppOptions = (): TAppOptions | undefined => {
|
140
140
|
return typeof this.appOptions === "function"
|
@@ -231,6 +231,15 @@ export class AppContext<TAttributes = any, TMagixEventPayloads = any, TAppOption
|
|
231
231
|
}
|
232
232
|
};
|
233
233
|
|
234
|
+
public removePage = async (index: number): Promise<boolean> => {
|
235
|
+
if (index < 0 || index >= this.pageState.length) {
|
236
|
+
console.warn(`[WindowManager]: page index ${index} out of range`);
|
237
|
+
return false;
|
238
|
+
}
|
239
|
+
this.appProxy.removeSceneByIndex(index);
|
240
|
+
return true;
|
241
|
+
}
|
242
|
+
|
234
243
|
public get pageState(): PageState {
|
235
244
|
return this.appProxy.pageState;
|
236
245
|
}
|
package/src/App/AppProxy.ts
CHANGED
@@ -27,11 +27,11 @@ import type { SceneState, View, SceneDefinition } from "white-web-sdk";
|
|
27
27
|
import type { AppManager } from "../AppManager";
|
28
28
|
import type { NetlessApp } from "../typings";
|
29
29
|
import type { ReadonlyTeleBox } from "@netless/telebox-insider";
|
30
|
-
import
|
30
|
+
import { calculateNextIndex, PageRemoveService, PageState } from "../Page";
|
31
31
|
|
32
32
|
export type AppEmitter = Emittery<AppEmitterEvent>;
|
33
33
|
|
34
|
-
export class AppProxy {
|
34
|
+
export class AppProxy implements PageRemoveService {
|
35
35
|
public kind: string;
|
36
36
|
public id: string;
|
37
37
|
public scenePath?: string;
|
@@ -249,6 +249,24 @@ export class AppProxy {
|
|
249
249
|
this.boxManager?.updateBoxState(currentAppState);
|
250
250
|
}
|
251
251
|
|
252
|
+
public async onRemoveScene(scenePath: string) {
|
253
|
+
if (this.scenePath && scenePath.startsWith(this.scenePath + "/")) {
|
254
|
+
let nextIndex = this.pageState.index;
|
255
|
+
let fullPath = this._pageState.getFullPath(nextIndex);
|
256
|
+
if (!fullPath) {
|
257
|
+
nextIndex = 0;
|
258
|
+
fullPath = this._pageState.getFullPath(nextIndex);
|
259
|
+
}
|
260
|
+
if (fullPath) {
|
261
|
+
this.setFullPath(fullPath);
|
262
|
+
}
|
263
|
+
this.setViewFocusScenePath();
|
264
|
+
if (this.view) {
|
265
|
+
this.view.focusSceneIndex = nextIndex;
|
266
|
+
}
|
267
|
+
}
|
268
|
+
}
|
269
|
+
|
252
270
|
public getAppInitState = (id: string) => {
|
253
271
|
const attrs = this.store.getAppState(id);
|
254
272
|
if (!attrs) return;
|
@@ -385,14 +403,47 @@ export class AppProxy {
|
|
385
403
|
return view;
|
386
404
|
}
|
387
405
|
|
388
|
-
public notifyPageStateChange = () => {
|
406
|
+
public notifyPageStateChange = debounce(() => {
|
389
407
|
this.appEmitter.emit("pageStateChange", this.pageState);
|
390
|
-
};
|
408
|
+
}, 50);
|
391
409
|
|
392
410
|
public get pageState(): PageState {
|
393
411
|
return this._pageState.toObject();
|
394
412
|
}
|
395
413
|
|
414
|
+
// PageRemoveService
|
415
|
+
public async removeSceneByIndex(index: number) {
|
416
|
+
const scenePath = this._pageState.getFullPath(index);
|
417
|
+
if (scenePath) {
|
418
|
+
// 不能删除所有场景
|
419
|
+
if (this.pageState.length <= 1) {
|
420
|
+
return false;
|
421
|
+
}
|
422
|
+
const nextIndex = calculateNextIndex(index, this.pageState);
|
423
|
+
// 只修改 focus path 不修改 FullPath
|
424
|
+
this.setSceneIndexWithoutSync(nextIndex);
|
425
|
+
this.manager.dispatchInternalEvent(Events.SetAppFocusIndex, {
|
426
|
+
type: "app",
|
427
|
+
appID: this.id,
|
428
|
+
index: nextIndex,
|
429
|
+
});
|
430
|
+
// 手动添加一个延迟, 让 app 切换场景后再删除以避免闪烁
|
431
|
+
setTimeout(() => {
|
432
|
+
removeScenes(this.manager.room, scenePath, index);
|
433
|
+
}, 100);
|
434
|
+
return true;
|
435
|
+
} else {
|
436
|
+
return false;
|
437
|
+
}
|
438
|
+
}
|
439
|
+
|
440
|
+
public setSceneIndexWithoutSync(index: number) {
|
441
|
+
if (this.view) {
|
442
|
+
this.view.focusSceneIndex = index;
|
443
|
+
}
|
444
|
+
}
|
445
|
+
// PageRemoveService end
|
446
|
+
|
396
447
|
public setSceneIndex(index: number) {
|
397
448
|
if (this.view) {
|
398
449
|
this.view.focusSceneIndex = index;
|
package/src/App/Storage/index.ts
CHANGED
@@ -37,15 +37,21 @@ export class Storage<TState extends Record<string, any> = any> implements Storag
|
|
37
37
|
this._state = {} as TState;
|
38
38
|
const rawState = this._getRawState(this._state);
|
39
39
|
|
40
|
-
if (this.
|
41
|
-
if (
|
42
|
-
if (
|
43
|
-
|
40
|
+
if (this._context.getIsWritable()) {
|
41
|
+
if (this.id === null) {
|
42
|
+
if (context.isAddApp && defaultState) {
|
43
|
+
this.setState(defaultState);
|
44
|
+
}
|
45
|
+
} else {
|
46
|
+
if (rawState === this._state || !isObject(rawState)) {
|
47
|
+
if (!get(this._context.getAttributes(), [STORAGE_NS])) {
|
48
|
+
this._context.updateAttributes([STORAGE_NS], {});
|
49
|
+
}
|
50
|
+
this._context.updateAttributes([STORAGE_NS, this.id], this._state);
|
51
|
+
if (defaultState) {
|
52
|
+
this.setState(defaultState);
|
53
|
+
}
|
44
54
|
}
|
45
|
-
this._context.updateAttributes([STORAGE_NS, this.id], this._state);
|
46
|
-
}
|
47
|
-
if (defaultState) {
|
48
|
-
this.setState(defaultState);
|
49
55
|
}
|
50
56
|
}
|
51
57
|
|
package/src/AppListener.ts
CHANGED
@@ -6,6 +6,13 @@ import { setViewFocusScenePath } from "./Utils/Common";
|
|
6
6
|
import type { AnimationMode, Camera, Event } from "white-web-sdk";
|
7
7
|
import type { AppManager } from "./AppManager";
|
8
8
|
import type { TeleBoxState } from "@netless/telebox-insider";
|
9
|
+
|
10
|
+
type SetAppFocusIndex = {
|
11
|
+
type: "main" | "app";
|
12
|
+
appID?: string;
|
13
|
+
index: number;
|
14
|
+
}
|
15
|
+
|
9
16
|
export class AppListeners {
|
10
17
|
private displayer = this.manager.displayer;
|
11
18
|
|
@@ -67,6 +74,10 @@ export class AppListeners {
|
|
67
74
|
this.initMainViewCameraHandler();
|
68
75
|
break;
|
69
76
|
}
|
77
|
+
case Events.SetAppFocusIndex: {
|
78
|
+
this.setAppFocusViewIndexHandler(data.payload);
|
79
|
+
break;
|
80
|
+
}
|
70
81
|
default:
|
71
82
|
break;
|
72
83
|
}
|
@@ -119,4 +130,15 @@ export class AppListeners {
|
|
119
130
|
private initMainViewCameraHandler = () => {
|
120
131
|
this.manager.mainViewProxy.addCameraReaction();
|
121
132
|
}
|
133
|
+
|
134
|
+
private setAppFocusViewIndexHandler = (payload: SetAppFocusIndex) => {
|
135
|
+
if (payload.type === "main") {
|
136
|
+
this.manager.setSceneIndexWithoutSync(payload.index);
|
137
|
+
} else if (payload.type === "app" && payload.appID) {
|
138
|
+
const app = this.manager.appProxies.get(payload.appID);
|
139
|
+
if (app) {
|
140
|
+
app.setSceneIndexWithoutSync(payload.index);
|
141
|
+
}
|
142
|
+
}
|
143
|
+
}
|
122
144
|
}
|