@netless/fastboard 0.0.10 → 0.2.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/LICENSE.txt +1 -1
- package/dist/index.js +32 -0
- package/dist/index.js.map +1 -0
- package/dist/index.mjs +7 -0
- package/dist/index.mjs.map +1 -0
- package/package.json +26 -79
- package/src/index.ts +2 -34
- package/README.md +0 -126
- package/dist/index.cjs.js +0 -14
- package/dist/index.cjs.js.map +0 -1
- package/dist/index.es.js +0 -2642
- package/dist/index.es.js.map +0 -1
- package/dist/svelte.cjs.js +0 -2
- package/dist/svelte.cjs.js.map +0 -1
- package/dist/svelte.es.js +0 -31
- package/dist/svelte.es.js.map +0 -1
- package/dist/vue.cjs.js +0 -2
- package/dist/vue.cjs.js.map +0 -1
- package/dist/vue.es.js +0 -42
- package/dist/vue.es.js.map +0 -1
- package/src/WhiteboardApp.ts +0 -146
- package/src/behaviors/register-apps.ts +0 -39
- package/src/behaviors/style.ts +0 -17
- package/src/components/PageControl.scss +0 -80
- package/src/components/PageControl.tsx +0 -181
- package/src/components/PlayerControl/PlayerControl.scss +0 -145
- package/src/components/PlayerControl/PlayerControl.tsx +0 -158
- package/src/components/PlayerControl/components/Button.tsx +0 -55
- package/src/components/PlayerControl/hooks.ts +0 -88
- package/src/components/PlayerControl/icons/Loading.tsx +0 -13
- package/src/components/PlayerControl/icons/Pause.tsx +0 -13
- package/src/components/PlayerControl/icons/Play.tsx +0 -13
- package/src/components/PlayerControl/icons/index.ts +0 -10
- package/src/components/PlayerControl/index.ts +0 -1
- package/src/components/RedoUndo.scss +0 -56
- package/src/components/RedoUndo.tsx +0 -95
- package/src/components/Root.scss +0 -55
- package/src/components/Root.tsx +0 -61
- package/src/components/Toolbar/Content.tsx +0 -93
- package/src/components/Toolbar/Toolbar.scss +0 -247
- package/src/components/Toolbar/Toolbar.tsx +0 -82
- package/src/components/Toolbar/components/ApplianceButtons.tsx +0 -132
- package/src/components/Toolbar/components/AppsButton.tsx +0 -106
- package/src/components/Toolbar/components/Button.tsx +0 -54
- package/src/components/Toolbar/components/ColorBox.tsx +0 -56
- package/src/components/Toolbar/components/CutLine.tsx +0 -8
- package/src/components/Toolbar/components/PencilButton.tsx +0 -70
- package/src/components/Toolbar/components/ShapesButton.tsx +0 -143
- package/src/components/Toolbar/components/Slider.tsx +0 -27
- package/src/components/Toolbar/components/TextButton.tsx +0 -66
- package/src/components/Toolbar/components/UpDownButtons.tsx +0 -49
- package/src/components/Toolbar/components/assets/cocos.png +0 -0
- package/src/components/Toolbar/components/assets/countdown.png +0 -0
- package/src/components/Toolbar/components/assets/geogebra.png +0 -0
- package/src/components/Toolbar/components/assets/vscode.png +0 -0
- package/src/components/Toolbar/const.ts +0 -32
- package/src/components/Toolbar/hooks.ts +0 -113
- package/src/components/Toolbar/icons/Apps.tsx +0 -16
- package/src/components/Toolbar/icons/Arrow.tsx +0 -16
- package/src/components/Toolbar/icons/Circle.tsx +0 -21
- package/src/components/Toolbar/icons/Clean.tsx +0 -16
- package/src/components/Toolbar/icons/Clicker.tsx +0 -19
- package/src/components/Toolbar/icons/Collapse.tsx +0 -17
- package/src/components/Toolbar/icons/Diamond.tsx +0 -17
- package/src/components/Toolbar/icons/Down.tsx +0 -17
- package/src/components/Toolbar/icons/Eraser.tsx +0 -16
- package/src/components/Toolbar/icons/Expand.tsx +0 -17
- package/src/components/Toolbar/icons/Line.tsx +0 -13
- package/src/components/Toolbar/icons/Pencil.tsx +0 -16
- package/src/components/Toolbar/icons/Rectangle.tsx +0 -13
- package/src/components/Toolbar/icons/Selector.tsx +0 -16
- package/src/components/Toolbar/icons/SpeechBalloon.tsx +0 -17
- package/src/components/Toolbar/icons/Star.tsx +0 -17
- package/src/components/Toolbar/icons/Text.tsx +0 -16
- package/src/components/Toolbar/icons/Triangle.tsx +0 -17
- package/src/components/Toolbar/icons/Up.tsx +0 -17
- package/src/components/Toolbar/icons/index.ts +0 -42
- package/src/components/Toolbar/index.ts +0 -1
- package/src/components/ZoomControl.scss +0 -80
- package/src/components/ZoomControl.tsx +0 -221
- package/src/i18n/en.json +0 -31
- package/src/i18n/index.ts +0 -22
- package/src/i18n/zh-CN.json +0 -32
- package/src/icons/ChevronLeft.tsx +0 -21
- package/src/icons/ChevronRight.tsx +0 -21
- package/src/icons/FilePlus.tsx +0 -18
- package/src/icons/Minus.tsx +0 -21
- package/src/icons/Plus.tsx +0 -21
- package/src/icons/Redo.tsx +0 -24
- package/src/icons/Reset.tsx +0 -23
- package/src/icons/Undo.tsx +0 -24
- package/src/icons/index.tsx +0 -11
- package/src/internal/Instance.tsx +0 -275
- package/src/internal/helpers.ts +0 -86
- package/src/internal/hooks.ts +0 -9
- package/src/internal/index.ts +0 -3
- package/src/internal/mount-whiteboard.ts +0 -90
- package/src/react.tsx +0 -52
- package/src/style.scss +0 -35
- package/src/svelte.ts +0 -45
- package/src/theme/index.ts +0 -36
- package/src/types/index.ts +0 -22
- package/src/vue.ts +0 -74
|
@@ -1,21 +0,0 @@
|
|
|
1
|
-
import type { IconProps } from "../types";
|
|
2
|
-
|
|
3
|
-
import React from "react";
|
|
4
|
-
import { themes } from "../theme";
|
|
5
|
-
|
|
6
|
-
export function ChevronLeft({ theme = "light", active }: IconProps) {
|
|
7
|
-
const config = themes[theme];
|
|
8
|
-
const stroke = active ? config.activeColor : config.color;
|
|
9
|
-
|
|
10
|
-
return (
|
|
11
|
-
<svg viewBox="0 0 24 24">
|
|
12
|
-
<path
|
|
13
|
-
fill="none"
|
|
14
|
-
stroke={stroke}
|
|
15
|
-
strokeLinecap="round"
|
|
16
|
-
strokeLinejoin="round"
|
|
17
|
-
d="m14 16-2-2-2-2 2-2 2-2"
|
|
18
|
-
/>
|
|
19
|
-
</svg>
|
|
20
|
-
);
|
|
21
|
-
}
|
|
@@ -1,21 +0,0 @@
|
|
|
1
|
-
import type { IconProps } from "../types";
|
|
2
|
-
|
|
3
|
-
import React from "react";
|
|
4
|
-
import { themes } from "../theme";
|
|
5
|
-
|
|
6
|
-
export function ChevronRight({ theme = "light", active }: IconProps) {
|
|
7
|
-
const config = themes[theme];
|
|
8
|
-
const stroke = active ? config.activeColor : config.color;
|
|
9
|
-
|
|
10
|
-
return (
|
|
11
|
-
<svg viewBox="0 0 24 24">
|
|
12
|
-
<path
|
|
13
|
-
fill="none"
|
|
14
|
-
stroke={stroke}
|
|
15
|
-
strokeLinecap="round"
|
|
16
|
-
strokeLinejoin="round"
|
|
17
|
-
d="m10 16 2-2 2-2-2-2-2-2"
|
|
18
|
-
/>
|
|
19
|
-
</svg>
|
|
20
|
-
);
|
|
21
|
-
}
|
package/src/icons/FilePlus.tsx
DELETED
|
@@ -1,18 +0,0 @@
|
|
|
1
|
-
import type { IconProps } from "../types";
|
|
2
|
-
|
|
3
|
-
import React from "react";
|
|
4
|
-
import { themes } from "../theme";
|
|
5
|
-
|
|
6
|
-
export function FilePlus({ theme = "light", active }: IconProps) {
|
|
7
|
-
const config = themes[theme];
|
|
8
|
-
const stroke = active ? config.activeColor : config.color;
|
|
9
|
-
|
|
10
|
-
return (
|
|
11
|
-
<svg viewBox="0 0 24 24">
|
|
12
|
-
<path
|
|
13
|
-
fill={stroke}
|
|
14
|
-
d="M12 7.5a.5.5 0 0 1 .09.992L12 8.5H8a1.5 1.5 0 0 0-1.493 1.356L6.5 10v6a1.5 1.5 0 0 0 1.356 1.493L8 17.5h6a1.5 1.5 0 0 0 1.493-1.356L15.5 16v-4a.5.5 0 0 1 .992-.09l.008.09v4a2.5 2.5 0 0 1-2.336 2.495L14 18.5H8a2.5 2.5 0 0 1-2.495-2.336L5.5 16v-6a2.5 2.5 0 0 1 2.336-2.495L8 7.5h4Zm4-2a.5.5 0 0 1 .492.41L16.5 6v1.5H18a.5.5 0 0 1 .09.992L18 8.5h-1.5V10a.5.5 0 0 1-.992.09L15.5 10V8.5H14a.5.5 0 0 1-.09-.992L14 7.5h1.5V6a.5.5 0 0 1 .5-.5Z"
|
|
15
|
-
/>
|
|
16
|
-
</svg>
|
|
17
|
-
);
|
|
18
|
-
}
|
package/src/icons/Minus.tsx
DELETED
|
@@ -1,21 +0,0 @@
|
|
|
1
|
-
import type { IconProps } from "../types";
|
|
2
|
-
|
|
3
|
-
import React from "react";
|
|
4
|
-
import { themes } from "../theme";
|
|
5
|
-
|
|
6
|
-
export function Minus({ theme = "light", active }: IconProps) {
|
|
7
|
-
const config = themes[theme];
|
|
8
|
-
const stroke = active ? config.activeColor : config.color;
|
|
9
|
-
|
|
10
|
-
return (
|
|
11
|
-
<svg viewBox="0 0 24 24">
|
|
12
|
-
<path
|
|
13
|
-
fill="none"
|
|
14
|
-
stroke={stroke}
|
|
15
|
-
strokeLinecap="round"
|
|
16
|
-
strokeLinejoin="round"
|
|
17
|
-
d="M7 12h10"
|
|
18
|
-
/>
|
|
19
|
-
</svg>
|
|
20
|
-
);
|
|
21
|
-
}
|
package/src/icons/Plus.tsx
DELETED
|
@@ -1,21 +0,0 @@
|
|
|
1
|
-
import type { IconProps } from "../types";
|
|
2
|
-
|
|
3
|
-
import React from "react";
|
|
4
|
-
import { themes } from "../theme";
|
|
5
|
-
|
|
6
|
-
export function Plus({ theme = "light", active }: IconProps) {
|
|
7
|
-
const config = themes[theme];
|
|
8
|
-
const stroke = active ? config.activeColor : config.color;
|
|
9
|
-
|
|
10
|
-
return (
|
|
11
|
-
<svg viewBox="0 0 24 24">
|
|
12
|
-
<path
|
|
13
|
-
fill="none"
|
|
14
|
-
stroke={stroke}
|
|
15
|
-
strokeLinecap="round"
|
|
16
|
-
strokeLinejoin="round"
|
|
17
|
-
d="M12 7v10m-5-5h10"
|
|
18
|
-
/>
|
|
19
|
-
</svg>
|
|
20
|
-
);
|
|
21
|
-
}
|
package/src/icons/Redo.tsx
DELETED
|
@@ -1,24 +0,0 @@
|
|
|
1
|
-
import type { IconProps } from "../types";
|
|
2
|
-
|
|
3
|
-
import React from "react";
|
|
4
|
-
import { themes } from "../theme";
|
|
5
|
-
|
|
6
|
-
export function Redo({ theme = "light", active }: IconProps) {
|
|
7
|
-
const config = themes[theme];
|
|
8
|
-
const stroke = active ? config.activeColor : config.color;
|
|
9
|
-
|
|
10
|
-
return (
|
|
11
|
-
<svg viewBox="0 0 24 24">
|
|
12
|
-
<g
|
|
13
|
-
fill="none"
|
|
14
|
-
fillRule="evenodd"
|
|
15
|
-
stroke={stroke}
|
|
16
|
-
strokeLinecap="round"
|
|
17
|
-
strokeLinejoin="round"
|
|
18
|
-
>
|
|
19
|
-
<path d="M14 14h4v-4" />
|
|
20
|
-
<path d="m18 14-.788-.9A7.005 7.005 0 0 0 6 14h0" />
|
|
21
|
-
</g>
|
|
22
|
-
</svg>
|
|
23
|
-
);
|
|
24
|
-
}
|
package/src/icons/Reset.tsx
DELETED
|
@@ -1,23 +0,0 @@
|
|
|
1
|
-
import type { IconProps } from "../types";
|
|
2
|
-
|
|
3
|
-
import React from "react";
|
|
4
|
-
import { themes } from "../theme";
|
|
5
|
-
|
|
6
|
-
export function Reset({ theme = "light", active }: IconProps) {
|
|
7
|
-
const config = themes[theme];
|
|
8
|
-
const stroke = active ? config.activeColor : config.color;
|
|
9
|
-
|
|
10
|
-
return (
|
|
11
|
-
<svg viewBox="0 0 24 24">
|
|
12
|
-
<g fill="none" fillRule="evenodd" transform="translate(-176 -684)">
|
|
13
|
-
<path
|
|
14
|
-
stroke={stroke}
|
|
15
|
-
strokeLinejoin="round"
|
|
16
|
-
d="M188 688v4m0 8v4m8-8h-4m-8 0h-4"
|
|
17
|
-
/>
|
|
18
|
-
<circle cx="188" cy="696" r="6" stroke={stroke} />
|
|
19
|
-
<circle cx="188" cy="696" r="1" fill={stroke} />
|
|
20
|
-
</g>
|
|
21
|
-
</svg>
|
|
22
|
-
);
|
|
23
|
-
}
|
package/src/icons/Undo.tsx
DELETED
|
@@ -1,24 +0,0 @@
|
|
|
1
|
-
import type { IconProps } from "../types";
|
|
2
|
-
|
|
3
|
-
import React from "react";
|
|
4
|
-
import { themes } from "../theme";
|
|
5
|
-
|
|
6
|
-
export function Undo({ theme = "light", active }: IconProps) {
|
|
7
|
-
const config = themes[theme];
|
|
8
|
-
const stroke = active ? config.activeColor : config.color;
|
|
9
|
-
|
|
10
|
-
return (
|
|
11
|
-
<svg viewBox="0 0 24 24">
|
|
12
|
-
<g
|
|
13
|
-
fill="none"
|
|
14
|
-
fillRule="evenodd"
|
|
15
|
-
stroke={stroke}
|
|
16
|
-
strokeLinecap="round"
|
|
17
|
-
strokeLinejoin="round"
|
|
18
|
-
>
|
|
19
|
-
<path d="M10 14H6v-4" />
|
|
20
|
-
<path d="m6 14 .788-.9A7.005 7.005 0 0 1 18 14h0" />
|
|
21
|
-
</g>
|
|
22
|
-
</svg>
|
|
23
|
-
);
|
|
24
|
-
}
|
package/src/icons/index.tsx
DELETED
|
@@ -1,11 +0,0 @@
|
|
|
1
|
-
import React from "react";
|
|
2
|
-
|
|
3
|
-
export interface IconPropsWithFallback {
|
|
4
|
-
fallback: React.ReactElement;
|
|
5
|
-
src?: string;
|
|
6
|
-
alt?: string;
|
|
7
|
-
}
|
|
8
|
-
|
|
9
|
-
export function Icon({ fallback, src, alt = "[icon]" }: IconPropsWithFallback) {
|
|
10
|
-
return src ? <img src={src} alt={alt} title={alt} /> : fallback;
|
|
11
|
-
}
|
|
@@ -1,275 +0,0 @@
|
|
|
1
|
-
import type { Mutable } from "type-fest";
|
|
2
|
-
import type { WindowManager } from "@netless/window-manager";
|
|
3
|
-
import type { Room, SceneDefinition, WhiteWebSdk } from "white-web-sdk";
|
|
4
|
-
import type { JoinRoom, ManagerConfig, SdkConfig } from "./mount-whiteboard";
|
|
5
|
-
import type { i18n } from "i18next";
|
|
6
|
-
|
|
7
|
-
import React, { createContext, useContext } from "react";
|
|
8
|
-
import ReactDOM from "react-dom";
|
|
9
|
-
import { BuiltinApps } from "@netless/window-manager";
|
|
10
|
-
|
|
11
|
-
import { Root } from "../components/Root";
|
|
12
|
-
import { mountWhiteboard } from "./mount-whiteboard";
|
|
13
|
-
import { noop } from "./helpers";
|
|
14
|
-
|
|
15
|
-
export interface AcceptParams {
|
|
16
|
-
readonly sdk: WhiteWebSdk;
|
|
17
|
-
readonly room: Room;
|
|
18
|
-
readonly manager: WindowManager;
|
|
19
|
-
readonly i18n: i18n;
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
export interface InsertMediaParams {
|
|
23
|
-
title: string;
|
|
24
|
-
src: string;
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
export interface InsertDocsStatic {
|
|
28
|
-
readonly fileType: "pdf" | "ppt";
|
|
29
|
-
readonly scenePath: string;
|
|
30
|
-
readonly scenes: SceneDefinition[];
|
|
31
|
-
readonly title?: string;
|
|
32
|
-
}
|
|
33
|
-
|
|
34
|
-
export interface InsertDocsDynamic {
|
|
35
|
-
readonly fileType: "pptx";
|
|
36
|
-
readonly scenePath: string;
|
|
37
|
-
readonly taskId: string;
|
|
38
|
-
readonly title?: string;
|
|
39
|
-
readonly url?: string;
|
|
40
|
-
readonly scenes?: SceneDefinition[];
|
|
41
|
-
}
|
|
42
|
-
|
|
43
|
-
export type InsertDocsParams = InsertDocsStatic | InsertDocsDynamic;
|
|
44
|
-
|
|
45
|
-
export type Language = "zh-CN" | "en-US";
|
|
46
|
-
|
|
47
|
-
export interface Layout {
|
|
48
|
-
Toolbar?: boolean;
|
|
49
|
-
PageControl?: boolean;
|
|
50
|
-
RedoUndo?: boolean;
|
|
51
|
-
ZoomControl?: boolean;
|
|
52
|
-
}
|
|
53
|
-
|
|
54
|
-
export interface WhiteboardAppConfig {
|
|
55
|
-
readonly sdkConfig: SdkConfig;
|
|
56
|
-
readonly joinRoom: JoinRoom;
|
|
57
|
-
readonly managerConfig?: Omit<ManagerConfig, "container">;
|
|
58
|
-
readonly layout?: Layout;
|
|
59
|
-
readonly toolbar?: {
|
|
60
|
-
apps?: {
|
|
61
|
-
enable?: boolean;
|
|
62
|
-
content?: React.ReactNode;
|
|
63
|
-
onClick?: () => void;
|
|
64
|
-
};
|
|
65
|
-
};
|
|
66
|
-
readonly language?: Language;
|
|
67
|
-
}
|
|
68
|
-
|
|
69
|
-
export interface Essentials {
|
|
70
|
-
readonly sdk: WhiteWebSdk;
|
|
71
|
-
readonly room: Room;
|
|
72
|
-
readonly manager: WindowManager;
|
|
73
|
-
readonly i18n: i18n;
|
|
74
|
-
}
|
|
75
|
-
|
|
76
|
-
export class Instance {
|
|
77
|
-
static readonly Context = createContext<Instance | null>(null);
|
|
78
|
-
|
|
79
|
-
config: Mutable<WhiteboardAppConfig>;
|
|
80
|
-
|
|
81
|
-
sdk: WhiteWebSdk | null = null;
|
|
82
|
-
room: Room | null = null;
|
|
83
|
-
manager: WindowManager | null = null;
|
|
84
|
-
i18n: i18n | null = null;
|
|
85
|
-
|
|
86
|
-
ready = false;
|
|
87
|
-
resolveReady!: () => void;
|
|
88
|
-
readyPromise!: Promise<void>;
|
|
89
|
-
|
|
90
|
-
refreshReadyPromise() {
|
|
91
|
-
this.readyPromise = new Promise<void>(resolve => {
|
|
92
|
-
this.resolveReady = () => {
|
|
93
|
-
this.resolveReady = noop;
|
|
94
|
-
this.ready = true;
|
|
95
|
-
resolve();
|
|
96
|
-
};
|
|
97
|
-
});
|
|
98
|
-
}
|
|
99
|
-
|
|
100
|
-
constructor(config: WhiteboardAppConfig) {
|
|
101
|
-
this.config = { ...config };
|
|
102
|
-
this.refreshReadyPromise();
|
|
103
|
-
this.initialize();
|
|
104
|
-
}
|
|
105
|
-
|
|
106
|
-
async initialize() {
|
|
107
|
-
const essentials = await mountWhiteboard(
|
|
108
|
-
this.config.sdkConfig,
|
|
109
|
-
this.config.joinRoom,
|
|
110
|
-
this.config.managerConfig || {},
|
|
111
|
-
this.config.language || "en-US"
|
|
112
|
-
);
|
|
113
|
-
this.accept(essentials);
|
|
114
|
-
this.resolveReady();
|
|
115
|
-
}
|
|
116
|
-
|
|
117
|
-
target: HTMLElement | null = null;
|
|
118
|
-
collector: HTMLElement | null = null;
|
|
119
|
-
|
|
120
|
-
bindElement(target: HTMLElement | null) {
|
|
121
|
-
if (this.target && this.target !== target) {
|
|
122
|
-
ReactDOM.unmountComponentAtNode(this.target);
|
|
123
|
-
}
|
|
124
|
-
this.target = target;
|
|
125
|
-
this.forceUpdate();
|
|
126
|
-
}
|
|
127
|
-
|
|
128
|
-
bindCollector(collector: HTMLElement | null) {
|
|
129
|
-
this.collector = collector;
|
|
130
|
-
if (this.manager && collector) {
|
|
131
|
-
this.manager.bindCollectorContainer(collector);
|
|
132
|
-
}
|
|
133
|
-
}
|
|
134
|
-
|
|
135
|
-
updateLayout(layout: Layout | undefined) {
|
|
136
|
-
this.config.layout = layout;
|
|
137
|
-
this.forceUpdate();
|
|
138
|
-
}
|
|
139
|
-
|
|
140
|
-
async forceUpdate() {
|
|
141
|
-
await this.readyPromise;
|
|
142
|
-
if (this.target) {
|
|
143
|
-
ReactDOM.render(<Root instance={this} />, this.target);
|
|
144
|
-
}
|
|
145
|
-
}
|
|
146
|
-
|
|
147
|
-
accept({ sdk, room, manager, i18n }: AcceptParams) {
|
|
148
|
-
this.sdk = sdk;
|
|
149
|
-
this.room = room;
|
|
150
|
-
this.manager = manager;
|
|
151
|
-
this.i18n = i18n;
|
|
152
|
-
this.forceUpdate();
|
|
153
|
-
}
|
|
154
|
-
|
|
155
|
-
async dispose() {
|
|
156
|
-
if (this.room) {
|
|
157
|
-
await this.unmount();
|
|
158
|
-
}
|
|
159
|
-
if (this.target) {
|
|
160
|
-
ReactDOM.unmountComponentAtNode(this.target);
|
|
161
|
-
this.sdk = this.room = this.manager = this.target = null;
|
|
162
|
-
}
|
|
163
|
-
}
|
|
164
|
-
|
|
165
|
-
async mount(node: HTMLElement) {
|
|
166
|
-
await this.readyPromise;
|
|
167
|
-
if (!this.manager) {
|
|
168
|
-
throw new Error(`[WhiteboardApp] mounted, but not found window manager`);
|
|
169
|
-
}
|
|
170
|
-
this.manager.bindContainer(node);
|
|
171
|
-
if (this.collector) {
|
|
172
|
-
this.manager.bindCollectorContainer(this.collector);
|
|
173
|
-
}
|
|
174
|
-
}
|
|
175
|
-
|
|
176
|
-
async unmount() {
|
|
177
|
-
if (this.manager) {
|
|
178
|
-
this.manager.destroy();
|
|
179
|
-
this.manager = null;
|
|
180
|
-
}
|
|
181
|
-
if (this.room) {
|
|
182
|
-
try {
|
|
183
|
-
await this.room.disconnect();
|
|
184
|
-
} catch {
|
|
185
|
-
// ignore any error on disconnecting
|
|
186
|
-
}
|
|
187
|
-
this.room = null;
|
|
188
|
-
}
|
|
189
|
-
this.refreshReadyPromise();
|
|
190
|
-
}
|
|
191
|
-
|
|
192
|
-
insertDocs(params: InsertDocsParams) {
|
|
193
|
-
if (!this.manager) {
|
|
194
|
-
throw new Error(`[WhiteboardApp] cannot insert doc before mounted`);
|
|
195
|
-
}
|
|
196
|
-
switch (params.fileType) {
|
|
197
|
-
case "pdf":
|
|
198
|
-
case "ppt":
|
|
199
|
-
return this.manager.addApp({
|
|
200
|
-
kind: "DocsViewer",
|
|
201
|
-
options: {
|
|
202
|
-
scenePath: params.scenePath,
|
|
203
|
-
title: params.title,
|
|
204
|
-
scenes: params.scenes,
|
|
205
|
-
},
|
|
206
|
-
});
|
|
207
|
-
case "pptx":
|
|
208
|
-
return this.manager.addApp({
|
|
209
|
-
kind: "Slide",
|
|
210
|
-
options: {
|
|
211
|
-
scenePath: params.scenePath,
|
|
212
|
-
title: params.title,
|
|
213
|
-
scenes: params.scenes,
|
|
214
|
-
},
|
|
215
|
-
attributes: {
|
|
216
|
-
taskId: params.taskId,
|
|
217
|
-
url: params.url,
|
|
218
|
-
},
|
|
219
|
-
});
|
|
220
|
-
}
|
|
221
|
-
}
|
|
222
|
-
|
|
223
|
-
insertCodeEditor() {
|
|
224
|
-
if (!this.manager) {
|
|
225
|
-
throw new Error(`[WhiteboardApp] cannot insert app before mounted`);
|
|
226
|
-
}
|
|
227
|
-
return this.manager.addApp({
|
|
228
|
-
kind: "Monaco",
|
|
229
|
-
options: { title: "Code Editor" },
|
|
230
|
-
});
|
|
231
|
-
}
|
|
232
|
-
|
|
233
|
-
insertGeoGebra() {
|
|
234
|
-
if (!this.manager) {
|
|
235
|
-
throw new Error(`[WhiteboardApp] cannot insert app before mounted`);
|
|
236
|
-
}
|
|
237
|
-
return this.manager.addApp({
|
|
238
|
-
kind: "GeoGebra",
|
|
239
|
-
options: { title: "GeoGebra" },
|
|
240
|
-
});
|
|
241
|
-
}
|
|
242
|
-
|
|
243
|
-
insertCountdown() {
|
|
244
|
-
if (!this.manager) {
|
|
245
|
-
throw new Error(`[WhiteboardApp] cannot insert app before mounted`);
|
|
246
|
-
}
|
|
247
|
-
return this.manager.addApp({
|
|
248
|
-
kind: "Countdown",
|
|
249
|
-
options: { title: "Countdown" },
|
|
250
|
-
});
|
|
251
|
-
}
|
|
252
|
-
|
|
253
|
-
insertMedia({ title, src }: InsertMediaParams) {
|
|
254
|
-
if (!this.manager) {
|
|
255
|
-
throw new Error(`[WhiteboardApp] cannot insert app before mounted`);
|
|
256
|
-
}
|
|
257
|
-
return this.manager.addApp({
|
|
258
|
-
kind: BuiltinApps.MediaPlayer,
|
|
259
|
-
options: { title },
|
|
260
|
-
attributes: { src },
|
|
261
|
-
});
|
|
262
|
-
}
|
|
263
|
-
|
|
264
|
-
async changeLanguage(language: Language) {
|
|
265
|
-
try {
|
|
266
|
-
await this.i18n?.changeLanguage(language);
|
|
267
|
-
} finally {
|
|
268
|
-
await this.forceUpdate();
|
|
269
|
-
}
|
|
270
|
-
}
|
|
271
|
-
}
|
|
272
|
-
|
|
273
|
-
export function useInstance() {
|
|
274
|
-
return useContext(Instance.Context);
|
|
275
|
-
}
|
package/src/internal/helpers.ts
DELETED
|
@@ -1,86 +0,0 @@
|
|
|
1
|
-
import type { SceneDefinition } from "white-web-sdk";
|
|
2
|
-
|
|
3
|
-
export function noop() {
|
|
4
|
-
return;
|
|
5
|
-
}
|
|
6
|
-
|
|
7
|
-
export function applyStyles(css: string) {
|
|
8
|
-
const el = document.createElement("style");
|
|
9
|
-
el.appendChild(document.createTextNode(css));
|
|
10
|
-
document.head.appendChild(el);
|
|
11
|
-
return el;
|
|
12
|
-
}
|
|
13
|
-
|
|
14
|
-
export function clamp(value: number, min: number, max: number) {
|
|
15
|
-
return value < min ? min : value > max ? max : value;
|
|
16
|
-
}
|
|
17
|
-
|
|
18
|
-
export function isEqualArray<T>(a: T[], b: T[]) {
|
|
19
|
-
return a.length === b.length && a.every((e, i) => e === b[i]);
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
export type TaskFn = () => Promise<void> | void;
|
|
23
|
-
|
|
24
|
-
export class Lock {
|
|
25
|
-
running = false;
|
|
26
|
-
private nextFn: TaskFn | null = null;
|
|
27
|
-
schedule(fn: TaskFn) {
|
|
28
|
-
if (this.running) {
|
|
29
|
-
this.nextFn = fn;
|
|
30
|
-
} else {
|
|
31
|
-
this.running = true;
|
|
32
|
-
Promise.resolve(fn()).then(this.step);
|
|
33
|
-
}
|
|
34
|
-
}
|
|
35
|
-
private step = () => {
|
|
36
|
-
if (this.nextFn) {
|
|
37
|
-
const fn = this.nextFn;
|
|
38
|
-
this.nextFn = null;
|
|
39
|
-
Promise.resolve(fn()).then(this.step);
|
|
40
|
-
} else {
|
|
41
|
-
this.running = false;
|
|
42
|
-
}
|
|
43
|
-
};
|
|
44
|
-
}
|
|
45
|
-
|
|
46
|
-
// Copy from https://github.com/crimx/side-effect-manager/blob/main/src/gen-uid.ts
|
|
47
|
-
const SOUP =
|
|
48
|
-
"!#%()*+,-./:;=?@[]^_`{|}~" +
|
|
49
|
-
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789";
|
|
50
|
-
const SOUP_LEN = SOUP.length;
|
|
51
|
-
const ID_LEN = 20;
|
|
52
|
-
const reusedIdCarrier = Array(ID_LEN);
|
|
53
|
-
|
|
54
|
-
export const genUID = (): string => {
|
|
55
|
-
for (let i = 0; i < ID_LEN; i++) {
|
|
56
|
-
reusedIdCarrier[i] = SOUP.charAt(Math.random() * SOUP_LEN);
|
|
57
|
-
}
|
|
58
|
-
return reusedIdCarrier.join("");
|
|
59
|
-
};
|
|
60
|
-
|
|
61
|
-
export function makeSlideParams(scenes: SceneDefinition[]) {
|
|
62
|
-
const scenesWithoutPPT: SceneDefinition[] = [];
|
|
63
|
-
let taskId = "";
|
|
64
|
-
let url = "";
|
|
65
|
-
|
|
66
|
-
// e.g. "ppt(x)://cdn/prefix/dynamicConvert/{taskId}/1.slide"
|
|
67
|
-
const pptSrcRE = /^pptx?(?<prefix>:\/\/\S+?dynamicConvert)\/(?<taskId>\w+)\//;
|
|
68
|
-
|
|
69
|
-
for (const { name, ppt } of scenes) {
|
|
70
|
-
// make sure scenesWithoutPPT.length === scenes.length
|
|
71
|
-
scenesWithoutPPT.push({ name });
|
|
72
|
-
|
|
73
|
-
if (!ppt || !ppt.src.startsWith("ppt")) {
|
|
74
|
-
continue;
|
|
75
|
-
}
|
|
76
|
-
const match = pptSrcRE.exec(ppt.src);
|
|
77
|
-
if (!match || !match.groups) {
|
|
78
|
-
continue;
|
|
79
|
-
}
|
|
80
|
-
taskId = match.groups.taskId;
|
|
81
|
-
url = "https" + match.groups.prefix;
|
|
82
|
-
break;
|
|
83
|
-
}
|
|
84
|
-
|
|
85
|
-
return { scenesWithoutPPT, taskId, url };
|
|
86
|
-
}
|
package/src/internal/hooks.ts
DELETED
package/src/internal/index.ts
DELETED
|
@@ -1,90 +0,0 @@
|
|
|
1
|
-
import type { MountParams } from "@netless/window-manager";
|
|
2
|
-
import type {
|
|
3
|
-
JoinRoomParams,
|
|
4
|
-
RoomCallbacks,
|
|
5
|
-
WhiteWebSdkConfiguration,
|
|
6
|
-
} from "white-web-sdk";
|
|
7
|
-
import type { Essentials, Language } from "./Instance";
|
|
8
|
-
|
|
9
|
-
import { WindowManager } from "@netless/window-manager";
|
|
10
|
-
import { DefaultHotKeys, WhiteWebSdk } from "white-web-sdk";
|
|
11
|
-
import { createI18n } from "../i18n";
|
|
12
|
-
|
|
13
|
-
export type SdkConfig = Omit<
|
|
14
|
-
WhiteWebSdkConfiguration,
|
|
15
|
-
"useMobXState" | "disableNewPencil" | "disableMagixEventDispatchLimit"
|
|
16
|
-
>;
|
|
17
|
-
export type JoinRoom = Omit<
|
|
18
|
-
JoinRoomParams,
|
|
19
|
-
"useMultiViews" | "disableMagixEventDispatchLimit"
|
|
20
|
-
> & { callbacks?: Partial<RoomCallbacks> };
|
|
21
|
-
export type ManagerConfig = Omit<MountParams, "room">;
|
|
22
|
-
|
|
23
|
-
function ensureWindowManager(joinRoom: JoinRoom) {
|
|
24
|
-
if (
|
|
25
|
-
!joinRoom.invisiblePlugins ||
|
|
26
|
-
!joinRoom.invisiblePlugins.includes(WindowManager)
|
|
27
|
-
) {
|
|
28
|
-
joinRoom.invisiblePlugins = [
|
|
29
|
-
...(joinRoom.invisiblePlugins || []),
|
|
30
|
-
WindowManager,
|
|
31
|
-
];
|
|
32
|
-
}
|
|
33
|
-
}
|
|
34
|
-
|
|
35
|
-
export const defaultHotKeys = {
|
|
36
|
-
changeToSelector: "s",
|
|
37
|
-
changeToLaserPointer: "z",
|
|
38
|
-
changeToPencil: "p",
|
|
39
|
-
changeToRectangle: "r",
|
|
40
|
-
changeToEllipse: "c",
|
|
41
|
-
changeToEraser: "e",
|
|
42
|
-
changeToText: "t",
|
|
43
|
-
changeToStraight: "l",
|
|
44
|
-
changeToArrow: "a",
|
|
45
|
-
changeToHand: "h",
|
|
46
|
-
};
|
|
47
|
-
|
|
48
|
-
export async function mountWhiteboard(
|
|
49
|
-
sdkConfig: SdkConfig,
|
|
50
|
-
joinRoom: JoinRoom,
|
|
51
|
-
managerConfig: ManagerConfig,
|
|
52
|
-
language: Language
|
|
53
|
-
): Promise<Essentials> {
|
|
54
|
-
const sdk = new WhiteWebSdk({
|
|
55
|
-
...sdkConfig,
|
|
56
|
-
useMobXState: true,
|
|
57
|
-
});
|
|
58
|
-
|
|
59
|
-
ensureWindowManager(joinRoom);
|
|
60
|
-
joinRoom = { ...joinRoom };
|
|
61
|
-
const callbacks = joinRoom.callbacks;
|
|
62
|
-
delete joinRoom.callbacks;
|
|
63
|
-
const joinRoomParams: JoinRoomParams = {
|
|
64
|
-
floatBar: true,
|
|
65
|
-
hotKeys: {
|
|
66
|
-
...DefaultHotKeys,
|
|
67
|
-
...defaultHotKeys,
|
|
68
|
-
},
|
|
69
|
-
...joinRoom,
|
|
70
|
-
useMultiViews: true,
|
|
71
|
-
disableNewPencil: false,
|
|
72
|
-
disableMagixEventDispatchLimit: true,
|
|
73
|
-
};
|
|
74
|
-
const room = await sdk.joinRoom(joinRoomParams, callbacks);
|
|
75
|
-
|
|
76
|
-
const manager = await WindowManager.mount({
|
|
77
|
-
cursor: true,
|
|
78
|
-
debug: import.meta.env.DEV,
|
|
79
|
-
...managerConfig,
|
|
80
|
-
room,
|
|
81
|
-
});
|
|
82
|
-
|
|
83
|
-
const i18n = await createI18n({ language });
|
|
84
|
-
|
|
85
|
-
if (import.meta.env.DEV) {
|
|
86
|
-
Object.assign(window, { sdk, room, manager });
|
|
87
|
-
}
|
|
88
|
-
|
|
89
|
-
return { sdk, room, manager, i18n };
|
|
90
|
-
}
|