@netless/window-manager 1.0.0-canary.21 → 1.0.0-canary.24
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 +5 -1
- package/dist/App/AppProxy.d.ts +2 -0
- package/dist/View/CameraSynchronizer.d.ts +1 -1
- package/dist/index.cjs.js +12 -12
- package/dist/index.es.js +123 -170
- package/dist/index.umd.js +12 -12
- package/dist/style.css +1 -1
- package/docs/app-context.md +89 -3
- package/package.json +1 -1
- package/src/App/AppContext.ts +14 -3
- package/src/App/AppProxy.ts +81 -140
- package/src/ReconnectRefresher.ts +5 -1
- package/src/View/CameraSynchronizer.ts +17 -26
- package/src/View/ViewSync.ts +3 -2
- package/src/style.css +1 -0
package/src/App/AppProxy.ts
CHANGED
@@ -71,6 +71,8 @@ export class AppProxy implements PageRemoveService {
|
|
71
71
|
public size$ = this.valManager.attach(new Val<ISize | undefined>(undefined));
|
72
72
|
public box$ = this.valManager.attach(new Val<ReadonlyTeleBox | undefined>(undefined));
|
73
73
|
public view$ = this.valManager.attach(new Val<View | undefined>(undefined));
|
74
|
+
public syncCamera$ = this.valManager.attach(new Val<boolean>(true));
|
75
|
+
public whiteBoardViewCreated$ = this.valManager.attach(new Val<boolean>(false));
|
74
76
|
|
75
77
|
constructor(
|
76
78
|
private params: BaseInsertParams,
|
@@ -112,101 +114,61 @@ export class AppProxy implements PageRemoveService {
|
|
112
114
|
this.size$.setValue(toJS(this.appAttributes.size));
|
113
115
|
this.addCameraReaction();
|
114
116
|
this.addSizeReaction();
|
115
|
-
this.sideEffectManager.add(() =>
|
116
|
-
combine([this.box$, this.view$]).subscribe(([box, view]) => {
|
117
|
-
if (box && view) {
|
118
|
-
if (!this.camera$.value) {
|
119
|
-
this.storeCamera({
|
120
|
-
centerX: null,
|
121
|
-
centerY: null,
|
122
|
-
scale: 1,
|
123
|
-
id: this.uid,
|
124
|
-
});
|
125
|
-
this.camera$.setValue(toJS(this.appAttributes.camera));
|
126
|
-
}
|
127
|
-
if (!this.size$.value && box.contentStageRect) {
|
128
|
-
const initialRect = this.computedInitialRect(box.contentStageRect);
|
129
|
-
const width = initialRect?.width || box.contentStageRect.width;
|
130
|
-
const height = initialRect?.height || box.contentStageRect.height;
|
131
|
-
this.storeSize({
|
132
|
-
id: this.uid,
|
133
|
-
width,
|
134
|
-
height,
|
135
|
-
});
|
136
|
-
this.size$.setValue(toJS(this.appAttributes.size));
|
137
|
-
}
|
138
|
-
this.viewSync = new ViewSync({
|
139
|
-
uid: this.uid,
|
140
|
-
view$: this.view$,
|
141
|
-
camera$: this.camera$,
|
142
|
-
size$: this.size$,
|
143
|
-
stageRect$: box._contentStageRect$,
|
144
|
-
storeCamera: this.storeCamera,
|
145
|
-
storeSize: this.storeSize
|
146
|
-
});
|
147
|
-
this.sideEffectManager.add(() => () => this.viewSync?.destroy());
|
148
|
-
}
|
149
|
-
})
|
150
|
-
);
|
151
117
|
this.sideEffectManager.add(() =>
|
152
118
|
emitter.on("memberStateChange", this.onMemberStateChange)
|
153
119
|
);
|
154
|
-
this.
|
155
|
-
|
156
|
-
|
157
|
-
|
158
|
-
|
159
|
-
|
160
|
-
|
161
|
-
|
162
|
-
() => this.appAttributes?.state.ratio,
|
163
|
-
box._ratio$,
|
164
|
-
),
|
165
|
-
createValSync(
|
166
|
-
() => this.appAttributes?.state.stageRatio,
|
167
|
-
box._stageRatio$,
|
168
|
-
),
|
169
|
-
createValSync(
|
170
|
-
() => this.appAttributes?.state.draggable,
|
171
|
-
box._draggable$,
|
172
|
-
),
|
173
|
-
createValSync(
|
174
|
-
() => this.appAttributes?.state.resizable,
|
175
|
-
box._resizable$,
|
176
|
-
),
|
177
|
-
box._visible$.reaction((visible, skipUpdate) => {
|
178
|
-
if (skipUpdate) {
|
179
|
-
return;
|
180
|
-
}
|
181
|
-
this.store.updateAppState(this.id, AppAttributes.Visible, visible);
|
182
|
-
}),
|
183
|
-
box._ratio$.reaction((ratio, skipUpdate) => {
|
184
|
-
console.log("ratio change", ratio, skipUpdate);
|
185
|
-
if (skipUpdate) {
|
186
|
-
return;
|
187
|
-
}
|
188
|
-
this.store.updateAppState(this.id, AppAttributes.Ratio, ratio);
|
189
|
-
}),
|
190
|
-
box._stageRatio$.reaction((stageRatio, skipUpdate) => {
|
191
|
-
if (skipUpdate) {
|
192
|
-
return;
|
120
|
+
this.sideEffectManager.add(() => [
|
121
|
+
this.syncCamera$.reaction(syncCamera => {
|
122
|
+
if (!syncCamera) {
|
123
|
+
if (this.viewSync) {
|
124
|
+
this.viewSync.destroy();
|
125
|
+
this.viewSync = undefined;
|
126
|
+
this.sideEffectManager.flush("camera");
|
127
|
+
this.sideEffectManager.flush("size");
|
193
128
|
}
|
194
|
-
|
195
|
-
|
196
|
-
|
197
|
-
|
198
|
-
|
199
|
-
|
200
|
-
|
201
|
-
|
202
|
-
|
203
|
-
|
204
|
-
|
205
|
-
|
206
|
-
|
207
|
-
|
208
|
-
|
209
|
-
|
129
|
+
}
|
130
|
+
}),
|
131
|
+
this.whiteBoardViewCreated$.reaction(created => {
|
132
|
+
if (created && this.box) {
|
133
|
+
if (!this.syncCamera$.value) return;
|
134
|
+
combine([this.box$, this.view$]).subscribe(([box, view]) => {
|
135
|
+
if (box && view) {
|
136
|
+
if (!this.camera$.value) {
|
137
|
+
this.storeCamera({
|
138
|
+
centerX: null,
|
139
|
+
centerY: null,
|
140
|
+
scale: 1,
|
141
|
+
id: this.uid,
|
142
|
+
});
|
143
|
+
this.camera$.setValue(toJS(this.appAttributes.camera));
|
144
|
+
}
|
145
|
+
if (!this.size$.value && box.contentStageRect) {
|
146
|
+
const initialRect = this.computedInitialRect(box.contentStageRect);
|
147
|
+
const width = initialRect?.width || box.contentStageRect.width;
|
148
|
+
const height = initialRect?.height || box.contentStageRect.height;
|
149
|
+
this.storeSize({
|
150
|
+
id: this.uid,
|
151
|
+
width,
|
152
|
+
height,
|
153
|
+
});
|
154
|
+
this.size$.setValue(toJS(this.appAttributes.size));
|
155
|
+
}
|
156
|
+
this.viewSync = new ViewSync({
|
157
|
+
uid: this.uid,
|
158
|
+
view$: this.view$,
|
159
|
+
camera$: this.camera$,
|
160
|
+
size$: this.size$,
|
161
|
+
stageRect$: box._contentStageRect$,
|
162
|
+
storeCamera: this.storeCamera,
|
163
|
+
storeSize: this.storeSize
|
164
|
+
});
|
165
|
+
this.sideEffectManager.add(() => () => this.viewSync?.destroy());
|
166
|
+
this.whiteBoardViewCreated$.destroy();
|
167
|
+
}
|
168
|
+
})
|
169
|
+
}
|
170
|
+
})
|
171
|
+
]);
|
210
172
|
}
|
211
173
|
|
212
174
|
public fireMemberStateChange = () => {
|
@@ -383,11 +345,6 @@ export class AppProxy implements PageRemoveService {
|
|
383
345
|
this.box$.setValue(box);
|
384
346
|
if (this.isAddApp && this.box) {
|
385
347
|
this.store.updateAppState(appId, AppAttributes.ZIndex, this.box.zIndex);
|
386
|
-
this.store.updateAppState(appId, AppAttributes.Visible, this.box.visible);
|
387
|
-
this.store.updateAppState(appId, AppAttributes.Ratio, this.box.ratio);
|
388
|
-
this.store.updateAppState(appId, AppAttributes.StageRatio, this.box.stageRatio);
|
389
|
-
this.store.updateAppState(appId, AppAttributes.Draggable, this.box.draggable);
|
390
|
-
this.store.updateAppState(appId, AppAttributes.Resizable, this.box.resizable);
|
391
348
|
this.boxManager.focusBox({ appId }, false);
|
392
349
|
}
|
393
350
|
} catch (error: any) {
|
@@ -520,32 +477,34 @@ export class AppProxy implements PageRemoveService {
|
|
520
477
|
}
|
521
478
|
|
522
479
|
private appAttributesUpdateListener = (appId: string) => {
|
523
|
-
this.
|
524
|
-
|
525
|
-
|
526
|
-
|
527
|
-
|
528
|
-
|
529
|
-
|
530
|
-
|
531
|
-
|
532
|
-
|
533
|
-
|
534
|
-
|
535
|
-
|
536
|
-
|
537
|
-
|
538
|
-
|
539
|
-
|
540
|
-
|
541
|
-
|
542
|
-
|
543
|
-
|
544
|
-
this.
|
545
|
-
|
546
|
-
|
547
|
-
|
548
|
-
|
480
|
+
this.sideEffectManager.add(() => [
|
481
|
+
this.manager.refresher.add(appId, () => {
|
482
|
+
return autorun(() => {
|
483
|
+
const attrs = this.manager.attributes[appId];
|
484
|
+
if (attrs) {
|
485
|
+
this.appEmitter.emit("attributesUpdate", attrs);
|
486
|
+
}
|
487
|
+
});
|
488
|
+
}),
|
489
|
+
this.manager.refresher.add(this.stateKey, () => {
|
490
|
+
return autorun(() => {
|
491
|
+
const appState = this.appAttributes?.state;
|
492
|
+
if (appState?.zIndex > 0 && appState.zIndex !== this.box?.zIndex) {
|
493
|
+
this.boxManager?.setZIndex(appId, appState.zIndex);
|
494
|
+
}
|
495
|
+
});
|
496
|
+
}),
|
497
|
+
this.manager.refresher.add(`${appId}-fullPath`, () => {
|
498
|
+
return autorun(() => {
|
499
|
+
const fullPath = this.appAttributes?.fullPath;
|
500
|
+
this.setFocusScenePathHandler(fullPath);
|
501
|
+
if (this.fullPath$.value !== fullPath) {
|
502
|
+
this.notifyPageStateChange();
|
503
|
+
this.fullPath$.setValue(fullPath);
|
504
|
+
}
|
505
|
+
});
|
506
|
+
}),
|
507
|
+
]);
|
549
508
|
};
|
550
509
|
|
551
510
|
private setFocusScenePathHandler = debounce((fullPath: string | undefined) => {
|
@@ -683,11 +642,6 @@ export class AppProxy implements PageRemoveService {
|
|
683
642
|
|
684
643
|
this.viewManager.destroyView(this.id);
|
685
644
|
this.manager.appStatus.delete(this.id);
|
686
|
-
this.manager.refresher.remove(this.id);
|
687
|
-
this.manager.refresher.remove(this.stateKey);
|
688
|
-
this.manager.refresher.remove(`${this.id}-fullPath`);
|
689
|
-
this.manager.refresher.remove(`${this.id}-camera`);
|
690
|
-
this.manager.refresher.remove(`${this.id}-size`);
|
691
645
|
this.valManager.destroy();
|
692
646
|
}
|
693
647
|
|
@@ -735,16 +689,3 @@ export class AppProxy implements PageRemoveService {
|
|
735
689
|
return this.destroy(true, true, false);
|
736
690
|
}
|
737
691
|
}
|
738
|
-
|
739
|
-
|
740
|
-
const createValSync = (expr: any, Val: Val): (() => void) => {
|
741
|
-
return reaction(
|
742
|
-
expr,
|
743
|
-
val => {
|
744
|
-
if (Val.value !== val && val !== undefined) {
|
745
|
-
Val.setValue(val, true);
|
746
|
-
}
|
747
|
-
},
|
748
|
-
{ fireImmediately: true }
|
749
|
-
);
|
750
|
-
};
|
@@ -46,7 +46,11 @@ export class ReconnectRefresher {
|
|
46
46
|
this.ctx.emitter.emit("startReconnect");
|
47
47
|
}
|
48
48
|
if (phase === RoomPhase.Connected && this.phase === RoomPhase.Reconnecting) {
|
49
|
-
this.room?.
|
49
|
+
if (this.room?.isWritable) {
|
50
|
+
this.room?.dispatchMagixEvent(EnsureReconnectEvent, {});
|
51
|
+
} else {
|
52
|
+
this.onReconnected();
|
53
|
+
}
|
50
54
|
}
|
51
55
|
this.phase = phase;
|
52
56
|
};
|
@@ -1,5 +1,5 @@
|
|
1
1
|
import { AnimationMode } from "white-web-sdk";
|
2
|
-
import {
|
2
|
+
import { isEqual, pick, throttle } from "lodash";
|
3
3
|
import type { TeleBoxRect } from "@netless/telebox-insider";
|
4
4
|
import type { Camera, View } from "white-web-sdk";
|
5
5
|
import type { ICamera, ISize } from "../AttributesDelegate";
|
@@ -14,12 +14,12 @@ export class CameraSynchronizer {
|
|
14
14
|
|
15
15
|
constructor(protected saveCamera: SaveCamera) {}
|
16
16
|
|
17
|
-
public setRect =
|
17
|
+
public setRect = (rect: TeleBoxRect) => {
|
18
18
|
this.rect = rect;
|
19
19
|
if (this.remoteCamera && this.remoteSize) {
|
20
20
|
this.onRemoteUpdate(this.remoteCamera, this.remoteSize);
|
21
21
|
}
|
22
|
-
}
|
22
|
+
}
|
23
23
|
|
24
24
|
public setView(view: View) {
|
25
25
|
this.view = view;
|
@@ -37,22 +37,17 @@ export class CameraSynchronizer {
|
|
37
37
|
scale = this.rect.height / size.height;
|
38
38
|
}
|
39
39
|
const nextScale = camera.scale * scale;
|
40
|
-
const
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
config.centerY = camera.centerY;
|
50
|
-
}
|
51
|
-
this.view?.moveCamera(config);
|
40
|
+
const config: Partial<Camera> & { animationMode: AnimationMode } = {
|
41
|
+
scale: nextScale,
|
42
|
+
animationMode: AnimationMode.Immediately,
|
43
|
+
}
|
44
|
+
if (camera.centerX !== null) {
|
45
|
+
config.centerX = camera.centerX;
|
46
|
+
}
|
47
|
+
if (camera.centerY !== null) {
|
48
|
+
config.centerY = camera.centerY;
|
52
49
|
}
|
53
|
-
moveCamera();
|
54
|
-
// TODO 直接调用 moveCamera 依然会出现 camera 错误的情况,这里暂时加一个 delay 保证 camera 是对的, 后续需要 SDK 进行修改
|
55
|
-
delay(moveCamera, 50);
|
50
|
+
this.view?.moveCamera(config);
|
56
51
|
}
|
57
52
|
}, 10);
|
58
53
|
|
@@ -62,14 +57,10 @@ export class CameraSynchronizer {
|
|
62
57
|
if (this.rect && this.remoteCamera && needMoveCamera) {
|
63
58
|
const scale = this.rect.width / size.width;
|
64
59
|
const nextScale = this.remoteCamera.scale * scale;
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
})
|
70
|
-
};
|
71
|
-
moveCamera();
|
72
|
-
delay(moveCamera, 50);
|
60
|
+
this.view?.moveCamera({
|
61
|
+
scale: nextScale,
|
62
|
+
animationMode: AnimationMode.Immediately,
|
63
|
+
})
|
73
64
|
}
|
74
65
|
}
|
75
66
|
|
package/src/View/ViewSync.ts
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
import { AnimationMode,
|
1
|
+
import { AnimationMode, ViewMode } from "white-web-sdk";
|
2
2
|
import { CameraSynchronizer } from "./CameraSynchronizer";
|
3
3
|
import { combine } from "value-enhancer";
|
4
4
|
import { isEqual } from "lodash";
|
@@ -93,7 +93,8 @@ export class ViewSync {
|
|
93
93
|
};
|
94
94
|
|
95
95
|
private onCameraUpdatedByDevice = (camera: Camera) => {
|
96
|
-
|
96
|
+
if (!camera) return;
|
97
|
+
this.synchronizer.onLocalCameraUpdate({ ...camera, id: this.context.uid });
|
97
98
|
const stage = this.context.stageRect$.value;
|
98
99
|
if (stage) {
|
99
100
|
const size = { width: stage.width, height: stage.height, id: this.context.uid };
|