import { ConnectionState, DisconnectedReason, CmdDataType, DSSession, DingRTCChannel, JoinParam } from '@dingrtc/channel'; export { ConnectionState, DisconnectedReason } from '@dingrtc/channel'; import { EventEmitter, Reporter } from '@dingrtc/shared'; import * as pdfjs_dist_types_src_display_api from 'pdfjs-dist/types/src/display/api'; import * as pdfjs_dist_types_src_display_display_utils from 'pdfjs-dist/types/src/display/display_utils'; import styleInject from '/Users/leolin/projects/work/onertc/oneRTC-worktree/node_modules/.pnpm/style-inject@0.3.0/node_modules/style-inject/dist/style-inject.es.js'; declare enum ResizeType { width = 0, height = 1, widthAndHeight = 2, none = 3 } /** * 图形被选中时,在外部提示框上可以被按住拖动的点 * * @export * @class OutlineResizeHandle */ declare class OutlineResizeHandle { getX: () => number; getY: () => number; cursorStyle: string; resizeType: ResizeType; renderSelf: boolean; static ResizeType: typeof ResizeType; constructor(getX: () => number, getY: () => number, cursorStyle: string, resizeType: ResizeType, renderSelf?: boolean); /** * transparent 为 true 会绘制透明样式, 用于测算点位 * @param renderContext * @param transparent 是否应用透明样式 */ render(renderContext: CanvasRenderingContext2D, transparent: boolean, scale: number): void; isPointInShape(x: number, y: number): boolean; } /** * 基础图形点位描述 */ declare class Model { points: Point[]; /** * 图形点位模型 * @param points */ constructor(points: Point[]); setPoints(points: Point[]): void; setPointAtIndex(index: number, point: Point): void; get minx(): number; get miny(): number; get maxx(): number; get maxy(): number; get width(): number; get height(): number; /** * 中心点位置 */ get center(): { x: number; y: number; }; /** * 以当前图形中心点为圆心旋转 * @param angle */ rotate(angle: number): Point[]; } declare enum ShapeType { Click = "click", Select = "select", Pen = "pen", Line = "line", Rect = "rect", Square = "square", Ellipse = "ellipse", Circle = "circle", Text = "text", Triangle = "triangle",// 三角形 Rhombic = "rhombic",// 菱形 Arrow = "arrow", Delete = "delete", Image = "image", Stamp = "stamp", Video = "video", Audio = "audio", Eraser = "eraser", Brush = "eraser", EraserIndicator = "eraserIndicator", LaserPointer = "laserPointer", Cursor = "cursor", Drag = "drag" } declare enum ShapeOrderType { back = "back", front = "front", normal = "normal", bg = "bg" } declare enum ShapeFillType { none = "none", color = "color" } declare enum ShapeLineType { solid = "solid", dashed = "dashed" } declare enum ShapeFontFormatType { normal = "normal", bold = "bold", italic = "italic", bold_italic = "bold_italic" } declare enum ShapeVisibleType { invisible = "0", visible = "1" } declare enum InteractionStatusType { default = 0, focused = 1, selected = 2, resizing = 3, rotating = 4, willBeDeleted = 5 } /** * 图形消息 */ interface IShapeData { name: string; pageId: string; shape: ShapeType; order: ShapeOrderType; orderTime: string; text?: string; data: string; visible: ShapeVisibleType; style?: string; font?: string; image?: string; video?: string; audio?: string; } /** * 图形消息 */ interface IShapeRgnData { name: string; pageId: string; shape: ShapeType; rgn: string; } /** * 所有图形的基础类型 * * shape 通过 shapeId + creator 唯一确定 */ declare abstract class BaseShape extends EventEmitter<{ requestRender: (shape: BaseShape) => void; }> { shapeId: string; readonly creator: string; readonly pageId: string; static GIF_RENDER_RATE: number; hash: number; get shouldRenderOutline(): boolean; protected emitRenderRequest(): void; private _order; get order(): ShapeOrderType; set order(order: ShapeOrderType); private _orderTime; get orderTime(): number; set orderTime(orderTime: number); rngReverse: { xReversed: boolean; yReversed: boolean; }; transformOriginalInfo?: BaseShape; resizeStartHandle?: Point & { resizeType: ResizeType; index: number; }; resizeOriginPosition?: Point; protected _visible: boolean; get visible(): boolean; set visible(visible: boolean); abstract get shapeType(): ShapeType; abstract clone(userId: string, shapeId: string): BaseShape; protected _interactionStatus: InteractionStatusType; get interactionStatus(): InteractionStatusType; set interactionStatus(interactionStatus: InteractionStatusType); get points(): Point[]; set points(points: Point[]); protected model: Model; /** * 用于消息通信时传输的 shape 序列号 */ get shapeSeq(): string; /** * @param points 图形点位信息 * @param shapeId 图形序列 * @param creator 创建者 uid * @param pageId 所属页面 id,不设置表示图形不属于任何页面 */ constructor(points: Point[], shapeId: string, creator: string, pageId?: string); /** * 是否可以被选中 */ abstract shouldSelectAfterAdd(): boolean; render(ctx: CanvasRenderingContext2D, options: { viewport: { minx: number; miny: number; maxx: number; maxy: number; }; scale: number; translate: number[]; wrapperDom: HTMLElement; lineWidth: number; insertType: ShapeType; forceRenderText: boolean; }): void; /** * 渲染图形(不包括边框和形变抓手按钮) * @param renderContext * @param options */ protected abstract renderShape(renderContext: CanvasRenderingContext2D, options: { viewport: { minx: number; miny: number; maxx: number; maxy: number; }; scale: number; translate: number[]; wrapperDom: HTMLElement; lineWidth: number; insertType: ShapeType; forceRenderText: boolean; }): void; /** * 当图形被选中或者被聚焦时,渲染图形外部边框;当图形被单选时显示图形的变形把手 */ renderOutline(ctx: CanvasRenderingContext2D, scale: number): void; /** * 图形是否在选的的rect范围内(任意一点出现在选的范围内即认为可见) * @param x * @param y * @param width * @param height * @returns */ private isShapeInRect; /** * 测试点位是否在图形边线上 * @param x 点位在 canvas 上的 x 坐标 * @param y 点位在 canvas 上的 y 坐标 * @param renderContext */ abstract isPointInShape(x: number, y: number): boolean; /** * 测试点位是否在图形边框矩形内 * @param x 点位在 canvas 上的 x 坐标 * @param y 点位在 canvas 上的 y 坐标 */ isPointInShapeRect(x: number, y: number): boolean; export(): ShapeReservedState; /** * 获取 rgn 信息,用来在设备之间传输,实现 shape 的移动和缩放 */ getRgnData(): string; get minx(): number; get miny(): number; get maxx(): number; get maxy(): number; get width(): number; get height(): number; /** * 中心点位置 */ get center(): { x: number; y: number; }; /** * deepcopy 存储变化开始时候的 points 位置 */ storeTransformStartPoints(): void; onMoveStart(): void; onMove(deltaX: number, deltaY: number): void; onMoveEnd(deltaX: number, deltaY: number): void; onResizeStart(x: number, y: number): void; onResize(deltaX: number, deltaY: number, shiftPressing: boolean): void; /** * 对所有的点位根据 resizeOriginPosition 进行缩放 * @param xRatio * @param yRatio * @param resizeOriginPosition */ resizeByRatio(xRatio: number, yRatio: number, resizeOriginPosition?: Point): void; private updateRgnReverse; onResizeEnd(deltaX: number, deltaY: number, shiftPressing: boolean): void; /** * 以中心点为基准旋转 * @param angle */ onRotate(angle: number): void; /** * outline 上的 resize 把手 */ get outlineResizeHandles(): OutlineResizeHandle[]; destructor(): void; genDrawMsg(name: string): IShapeData; genRgnMsg(name: string): IShapeRgnData; } /** * 橡皮擦范围指示器 */ declare class EraserIndicator extends BaseShape { clone(): BaseShape; get shapeType(): ShapeType; shouldSelectAfterAdd(): boolean; isPointInShape(): boolean; renderShape(ctx: CanvasRenderingContext2D, options: { scale: number; lineWidth: number; }): void; constructor(); } /** * 选择范围指示器 */ declare class SelectIndicator extends BaseShape { clone(): BaseShape; get shapeType(): ShapeType; private shapeStyle; shouldSelectAfterAdd(): boolean; isPointInShape(): boolean; renderShape(renderContext: CanvasRenderingContext2D, options: { insertType: ShapeType; }): void; constructor(); } type WBRoleType = 'Admin' | 'Attendee' | 'Viewer'; type ImageScalingMode = 'auto' | 'fillWidth' | 'fillHeight'; /** * 图片图形,普通普通会缓存img对象,背景图(order='bg')的图片不缓存img */ declare class Image extends BaseShape { imgUrl: string; clone(userId: string, shapeId: string): Image; private loadedUrl; private _img?; get img(): HTMLImageElement | undefined; set img(value: HTMLImageElement | undefined); private gifData?; private gifRenderInterval; get shapeType(): ShapeType; export(): ShapeReservedState; constructor(baseConfig: { points: Point[]; shapeId: string; creator: string; pageId: string; }, imgUrl: string); shouldSelectAfterAdd(): boolean; genDrawMsg(userName: string): IShapeData; loadImage(): Promise; isPointInShape(x: number, y: number): boolean; isGif(): any; renderShape(renderContext: CanvasRenderingContext2D): void; genRgnMsg(name: string): { pageId: string; name: string; shape: ShapeType; rgn: string; }; destructor(): void; } /** * 音视频元素抽象类,包含音视频元素基本api */ declare abstract class MediaShape extends BaseShape { mediaUrl: string; wrapperDom: HTMLDivElement; mediaElement: HTMLVideoElement | HTMLAudioElement; private _headerDom; private _switchButton; private _repeatPlay; /** * 是否重复播放 */ get repeatPlay(): boolean; set repeatPlay(value: boolean); shouldSelectAfterAdd(): boolean; export(): ShapeReservedState; private callbacks?; setCallback(callbacks: { onShapeFocused: (shape: MediaShape) => void; onShapeSelected: (shape: MediaShape) => void; onMediaUpdate: (shape: MediaShape) => void; }): void; /** * * @param points 点位 * @param shapeId 图形序列号 * @param creator 创建者 * @param pageId 所属画布 pageid * @param mediaUrl 媒体url */ constructor(baseConfig: { points: Point[]; shapeId: string; creator: string; pageId: string; }, mediaUrl: string); genDrawMsg(userName: string): IShapeData; private _onVideoStop; protected abstract _makeMediaElement(): HTMLVideoElement | HTMLAudioElement; private _onMouseMove; private _onClick; private _onVideoTimePlay; private _onVideoTimePause; private _onVideoTimeUpdate; get visible(): boolean; set visible(visible: boolean); isPointInShape(x: number, y: number): boolean; renderShape(ctx: CanvasRenderingContext2D, options: { viewport: { minx: number; miny: number; maxx: number; maxy: number; }; scale: number; translate: number[]; wrapperDom: HTMLElement; }): void; /** * 从dom中删除媒体元素 */ removeMediaDom(): void; destructor(): void; } /** * 激光笔 */ declare class LaserPointer extends BaseShape { clone(): BaseShape; get shapeType(): ShapeType; isPointInShape(): boolean; shouldSelectAfterAdd(): boolean; renderShape(renderContext: CanvasRenderingContext2D, options: { scale: number; }): void; } declare enum MouseType { draw = "draw", select = "select", delete = "delete", erase = "erase", text = "text", polygon = "polygon", laserPointer = "laserPointer", default = "default" } /** * 用户鼠标光标 */ declare class Cursor extends BaseShape { userName: string; cursorType: MouseType; private color; clone(): BaseShape; constructor(baseConfig: { points: Point[]; shapeId: string; creator: string; }, userName: string, cursorType: MouseType, color: string); shouldSelectAfterAdd(): boolean; updateCursor(x: number, y: number, color: string, type: MouseType): void; get shapeType(): ShapeType; isPointInShape(): boolean; renderShape(ctx: CanvasRenderingContext2D, options: { scale: number; }): void; } declare class ShapeHistory { actionType: HistoryActionType; shapeId: string; currentState: ShapeReservedState; lastState?: ShapeReservedState; shapeCreator: string; constructor(actionType: HistoryActionType, shapeId: string, currentState: ShapeReservedState, lastState?: ShapeReservedState); } declare class BatchHistory { actionType: HistoryActionType; shapeStates: { shapeId: string; currentState: ShapeReservedState; lastState?: ShapeReservedState; }[]; constructor(actionType: HistoryActionType, shapeStates: { shapeId: string; currentState: ShapeReservedState; lastState?: ShapeReservedState; }[]); } declare enum HistoryActionType { reveiveShape = 0, newShape = 1, hideShape = 2, rgnShape = 3, updateStyle = 4, updateText = 5, deleteShape = 6 } declare class History extends EventEmitter<{ 'history-changed': (state: { undo: boolean; redo: boolean; }) => void; }> { private undoList; private redoList; private emitHistoryEvent; saveHistory(shapeHistory: ShapeHistory): void; batchSave(batchHistory: BatchHistory): void; undo(): ShapeHistory | BatchHistory; redo(): ShapeHistory | BatchHistory; clearAll(): void; clearUserHistory(userId: string): void; clearShapeHistory(shapeId: string): void; canUndo(): boolean; canRedo(): boolean; } declare class Page extends EventEmitter<{ 'background-image-updated': () => void; 'page-content-updated': (page: Page) => void; }> { pageId: string; private shapes; private _backgroundColor; private _backgroundImage?; private _scale; private _translate; history: History; get scale(): number; set scale(value: number); get translate(): [number, number]; set translate(value: [number, number]); get miny(): number; get minx(): number; get visibleShapes(): BaseShape[]; get backgroundImage(): Image | undefined; set backgroundImage(value: Image | undefined); get backgroundColor(): string; set backgroundColor(value: string); addShape(shape: BaseShape): void; getShapeBySeq(shapeSeq: string, userId: string): BaseShape; /** * 根据 page 中shapes 的 order 分类以及时间重新排序 */ updateShapesOrder(): void; /** * 返回当前页面内所有图形,包括背景图 * @returns */ getShapes(): BaseShape[]; /** * 清除所有图形 */ clearShapes(): void; /** * 清除所有图形和背景图 */ clearPage(): void; /** * 清除背景图 */ clearBackgroundImage(): void; /** * 清除某个用户的背景图 */ clearUserBackgroundImage(userId: string): void; /** * 清除某个用户的图形 * @param userId */ clearUserShapes(userId: string): void; removeShape(shapeId: string): void; constructor(pageId: string); reset(): void; export(): { pageId: string; scale: number; translate: [number, number]; backgroundColor: string; backgroundImage: ShapeReservedState; shapes: ShapeReservedState[]; }; static restore(data: any): Page; private static restoreShapes; restoreShapes(shapeStates: ShapeReservedState[]): BaseShape[]; } interface IDomRect { x: number; y: number; width: number; height: number; top: number; right: number; bottom: number; left: number; } declare enum WBClearType { All = "all", DRAWS = "draws", BACKGROUND_IMAGE = "backgroundImage" } interface IWhiteboardManagerEvents { /** * 频道内创建了一个新的白板 */ 'whiteboard-start': (whiteboardId: string) => void; /** * 频道内关闭了一个白板 */ 'whiteboard-stop': (whiteboardId: string) => void; /** * 频道内创建了一个新的标注 */ 'annotation-start': (annotationId: string, sourceType: AnnotationSourceType) => void; /** * 频道内关闭了一个标注 */ 'annotation-stop': (annotationId: string, sourceType: AnnotationSourceType) => void; /** * SDK 与服务器的连接状态发生改变时的回调。 */ 'connection-state-change': (currentState: ConnectionState, prevState: ConnectionState, reason?: DisconnectedReason) => void; } /** * camera 代表摄像头, screen-cast 代表共享,external 代表自定义源 */ type AnnotationSourceType = 'camera' | 'screen-cast' | 'external'; interface IWhiteboardEvents { /** * 用户加入了白板/标注 */ 'user-join': (userId: string) => void; /** * 用户离开了白板/标注 */ 'user-leave': (userId: string) => void; /** * 文档加载失败 */ 'doc-load-failed': (docId: string, docName: string) => void; /** * 文档加载成功 */ 'doc-ready': (docId: string) => void; /** * 用户视角共享开始 */ 'user-vision-share-start': (userId: string) => void; /** * 用户视角共享结束 */ 'user-vision-share-stop': (userId: string) => void; /** * 本地视角共享停止 */ 'vision-lock-stop': () => void; /** * 视图窗口变化 */ 'viewport-updated': (scale: number, viewport: { minx: number; miny: number; maxx: number; maxy: number; }) => void; /** * 新增文档 */ 'doc-created': (docId: string) => void; /** * 切换文档 */ 'doc-switched': (docId: string) => void; /** * 删除文档 */ 'doc-deleted': (docId: string) => void; /** * 背景图片更新 */ 'background-image-updated': (docId: string, pageIndex: number, imgUrl: string) => void; /** * 文档页码变化 */ 'page-index-changed': (activeDocId: string, pageIndex: number, totalPages: number) => void; /** * 用户自己操作导致视图大小变化 */ 'viewport-updated-by-self': () => void; /** * undo或者redo记录变化时触发 */ 'history-changed': (canUndo: boolean, canRedo: boolean) => void; } declare enum DocBrowserMode { flip = "flip", scroll = "scroll" } declare enum DocType { 'normal' = "normal", 'externalDoc' = "externalDoc", 'h5' = "h5", 'pdf' = "pdf" } declare abstract class BaseDoc extends EventEmitter<{ requestRender: (docId: string) => void; 'viewport-updated': (docId: string) => void; 'page-index-changed': (docId: string) => void; }> { /** * 文档类型 */ abstract get type(): DocType; /** * 文档内所有页面是否共享缩放和平移属性 * * @type {boolean} */ abstract get sharePageSize(): boolean; /** * 是否可以增加、删除页面 */ abstract get canModifyPage(): boolean; createdEventNotEmited: boolean; docId: string; name: string; creator: string; pageVersion: number; fileKey?: string; private pages; private previousPageIndex; curPageId: string; maxSeq: number; protected _browseMode: DocBrowserMode; disableScale: boolean; get browseMode(): DocBrowserMode; set browseMode(mode: DocBrowserMode); pageSize: { width: number; height: number; }; private _scrollPages; get scrollPages(): number; set scrollPages(pages: number); get width(): number; get scrollPageHeight(): number; get scrollHeight(): number; get y(): number; get currentPageIndex(): number; set currentPageIndex(index: number); get currentPage(): Page; get totalPages(): number; get scale(): number; get translate(): number[]; sizeConfig: { width: number; height: number; limited: boolean; }; setSizeConfig(sizeConfig: { width: number; height: number; limited: boolean; }): void; get isSizeLimited(): boolean; getPageByPageId(pageId: string): any; getPageIndexByPageId(pageId: string): any; getPages(): Page[]; getPageAtIndex(index: number): Page; generateNewPageId(): string; addPage(page: Page, index?: number): void; removePage(index: number): void; /** * 监听 page 更新事件,向外部发送渲染请求 * @param page */ private setUpPageListeners; protected requestRender(): void; /** * 通知外部文档更新,需要重新渲染 */ private onPageUpdated; /** * 根据pageId列表更新page,本地多的删掉,少的新建page补齐 * @param pageIds */ regenerate(pageIds: string[]): void; constructor(pageInfo: { docId: string; name: string; creator: string; curPageId: string; pageVersion: number; sizeConfig?: { width: number; height: number; limited: boolean; }; fileKey?: string; browseMode: DocBrowserMode; }); setScrollY(y: number, wrapperRect: IDomRect): void; /** * 设置画板偏移 * @param x 水平方向偏移 * @param y 竖直方向偏移 (如果是pdf view,只能垂直方向移动) * @param smooth 是否平滑移动 * @param duration 平滑移动时间,默认 400 ms */ setTranslate(x: number, y: number, wrapperRect: IDomRect, smooth?: boolean, duration?: number): void; /** * 设置当前白板视图的缩放比例,可以选择是否已白板中心作为缩放原点 * @param nextScale 缩放比例 * @param scaleByPosition 是否以某个位置为中心缩放,默认开启,且以当前画板中心为中心缩放 * @param scalePosition 指定缩放中心位置,如果不指定,则以当前画板中心为中心缩放 */ setScale(nextScale: number, scaleByPosition: boolean, wrapperRect: IDomRect, scalePosition?: { x: number; y: number; }): void; setScaleAndTranslate(nextScale: number, translate: number[], limited: boolean, wrapperRect: IDomRect): void; /** * 设置本地视角信息 * @param visionInfo 视角信息 */ setDocViewport(visionInfo: { width: number; height: number; minx: number; miny: number; }, wrapperRect: IDomRect, page?: Page): void; /** * 获取 sizeConfig 下或 白板在"scroll"模式下的被限定,在当前画布大小下缩放居中之后真实的画布大小 * */ private getSizeConfigLimitSize; /** * 以 传入的点位更新当前白板页面 scale 比例,如果白板被限制大小,会自动计算出合适的 scale 和 translate * @param nextScale 要更新的 scale * @param originalX 缩放点的 x 坐标,点位是在白板 canvas 元素上的位置 * @param originalY 缩放点的 y 坐标,点位是在白板 canvas 元素上的位置 */ updateBoardWithNewScale: (nextScale: number, originalX: number, originalY: number, rect: IDomRect) => void; /** * 根据传入的translate 和 scale计算出视窗位置 */ private getPotentialViewportPosition; /** * 计算在被限定大小的情况下,在某个缩放值下,translate能取的极限值 * @param scale * @param viewport 限定的视窗位置 */ private getLimitedTranslate; scaleBoardFitBackgroundImage(page: Page, wrapperRect: IDomRect, bgScaleMode: ImageScalingMode): void; /** * 返回文档可见区域的坐标 */ getDocViewportPosition(wrapperRect: IDomRect): { minx: number; miny: number; maxx: number; maxy: number; }; export(): { docId: string; name: string; creator: string; pageIndex: number; pageVersion: number; pages: { pageId: string; scale: number; translate: [number, number]; backgroundColor: string; backgroundImage: ShapeReservedState; shapes: ShapeReservedState[]; }[]; fileKey: string; }; toJson(): { docId: string; name: string; creator: string; pageIndex: number; pageLength: number; fileKey: string; }; /** * 清除所有页面数据 */ clear(): void; clearPageById(pageId: string): void; /** * 清除某个用户所有图形 * @param userId */ clearUserShapes(userId: string): void; /** * 清除某个用户背景图 * @param userId */ clearUserBackgroundImage(userId: string): void; reset(): void; } interface PDFViewer { pageIndex: number; width: number; totalHeight: number; domRef: HTMLDivElement; state: 'notloaded' | 'loading' | 'loaded'; url: string; y: number; pdfPages: Map; /** * pdf 页面加载完之后按顺序保存每页的高度(累计高度),用于计算当前页面的高度 */ pageHightList: number[]; } /** * pdf 文档 */ declare class PdfDoc extends BaseDoc { pdfViewer: PDFViewer; static DOC_TYPE: DocType; get browseMode(): DocBrowserMode; set browseMode(mode: DocBrowserMode); get type(): DocType; get sharePageSize(): boolean; get canModifyPage(): boolean; get width(): number; get scrollHeight(): number; url: string; lastSyncY: number; /** * 缓存当前页面高度范围,减少计算页码运算 */ private currentPageMem; /** * 判断当前滚动位置是否在当前缓存的页面范围内 */ private isInCurrentMemPage; get currentPageIndex(): number; constructor(docInfo: { docId: string; name: string; creator: string; curPageId: string; pageVersion: number; fileKey?: string; browseMode: DocBrowserMode; }, pdfViewer: PDFViewer); load(): Promise; setScrollY(y: number, wrapperRect: IDomRect): void; setScaleAndTranslate(nextScale: number, translate: number[], limited: boolean, wrapperRect: IDomRect): void; createPdfLoadingPage(): void; centerPdfDoc(): void; protected getPdfVisiblePage(wrapperRect: IDomRect): { pagesNum: number; start: number; end: number; firstVisibleIndex: number; lastVisibleIndex: number; }; /** * 检测当前滚动位置,显示周围几张PDF图片 */ lazyLoadPdfPage: any; /** * 检测当前展示位置,如果当前位置的pfd未渲染,则开始渲染当前页面 */ lazyRenderPdfPage: any; } declare class PdfPlugin { static getDevicePixelRatio(): number; static loadPdf(url: string, doc: PdfDoc): Promise; private static preparePdfPage; static updatePdfWidth(doc: PdfDoc, newWidth: number): void; } var css_248z = ".dingrtc-wb-wrapper{height:100%;overflow:hidden;position:relative;width:100%}.dingrtc-wb-wrapper__laser-on audio,.dingrtc-wb-wrapper__laser-on video{pointer-events:none!important}.dingrtc-wb-wrapper__drag-on{cursor:grab!important}.dingrtc-wb-wrapper__draging{cursor:grabbing!important}.dingrtc-wb-wrapper .dingrtc-pdf-viewer{pointer-events:none;position:absolute;transform-origin:0 0;-webkit-user-select:none;-moz-user-select:none;user-select:none;z-index:0}.dingrtc-wb-wrapper .dingrtc-pdf-viewer__page{box-shadow:1px 1px 10px 5px rgba(0,0,0,.05);position:absolute}.dingrtc-wb-wrapper .dingrtc-pdf-viewer__page:not(:last-of-type):after{background-color:#777;bottom:0;content:\"\";height:1px;left:0;position:absolute;right:0;z-index:1}.dingrtc-wb-wrapper .dingrtc-pdf-viewer__page:before{bottom:10px;content:attr(data-i);font-size:26px;font-weight:700;position:absolute;right:10px;z-index:1}.dingrtc-wb-wrapper .dingrtc-pdf-viewer .p-pdf-skeletons{height:100%}.dingrtc-wb-wrapper .dingrtc-pdf-viewer .p-pdf-skeletons .p-pdf-skeleton{background-color:#fff;border-radius:6px;display:flex;flex-direction:column;height:50%;justify-content:center;margin:0 auto;min-height:532.8px;overflow:hidden;padding:50px 36px;position:relative;width:720px}.dingrtc-wb-wrapper .dingrtc-pdf-viewer .p-pdf-skeletons .p-pdf-skeleton>div{margin-bottom:36px}.dingrtc-wb-wrapper .dingrtc-pdf-viewer .p-pdf-skeletons .p-pdf-skeleton .p-pdf-skeleton__avator{border-radius:144px;height:144px;position:relative;width:144px}.dingrtc-wb-wrapper .dingrtc-pdf-viewer .p-pdf-skeletons .p-pdf-skeleton .p-pdf-skeleton__avator:after,.dingrtc-wb-wrapper .dingrtc-pdf-viewer .p-pdf-skeletons .p-pdf-skeleton .p-pdf-skeleton__avator:before{border-radius:10px;content:\" \";height:50.4px;left:calc(100% + 40px);position:absolute;top:0;width:288px}.dingrtc-wb-wrapper .dingrtc-pdf-viewer .p-pdf-skeletons .p-pdf-skeleton .p-pdf-skeleton__avator:after{top:93.6px;width:432px}.dingrtc-wb-wrapper .dingrtc-pdf-viewer .p-pdf-skeletons .p-pdf-skeleton .p-pdf-skeleton__content{border-radius:10px;height:43.2px;margin-bottom:200px;position:relative;width:504px}.dingrtc-wb-wrapper .dingrtc-pdf-viewer .p-pdf-skeletons .p-pdf-skeleton .p-pdf-skeleton__content:after,.dingrtc-wb-wrapper .dingrtc-pdf-viewer .p-pdf-skeletons .p-pdf-skeleton .p-pdf-skeleton__content:before{border-radius:10px;content:\" \";height:43.2px;left:0;position:absolute;top:93.6px;width:612px}.dingrtc-wb-wrapper .dingrtc-pdf-viewer .p-pdf-skeletons .p-pdf-skeleton .p-pdf-skeleton__content:after{top:187.2px;width:612px}.dingrtc-wb-wrapper .dingrtc-pdf-viewer .p-pdf-skeletons .p-pdf-skeleton div,.dingrtc-wb-wrapper .dingrtc-pdf-viewer .p-pdf-skeletons .p-pdf-skeleton div:after,.dingrtc-wb-wrapper .dingrtc-pdf-viewer .p-pdf-skeletons .p-pdf-skeleton div:before{animation:loading 2s ease-in-out infinite;background-color:#ededed;background:linear-gradient(100deg,hsla(0,0%,100%,0) 40%,hsla(0,0%,100%,.5) 50%,hsla(0,0%,100%,0) 60%) #ededed;background-position-x:180%;background-size:200% 100%}@keyframes loading{to{background-position-x:-20%}}.dingrtc-wb-wrapper .dingrtc-wb-render-fps{color:#333;font-size:12px;position:absolute;right:30px;top:60px;z-index:1}.dingrtc-wb-wrapper .dingrtc-wb-render-fps img{display:block}.dingrtc-wb-wrapper .dingrtc-wb__bg-img{pointer-events:none;z-index:0}.dingrtc-wb-wrapper .dingrtc-wb__bg-img,.dingrtc-wb-wrapper .dingrtc-wb__media{position:absolute;transform-origin:0 0;-webkit-user-select:none;-moz-user-select:none;user-select:none}.dingrtc-wb-wrapper .dingrtc-wb__media{background-color:transparent;overflow:hidden;padding:1px;z-index:1}.dingrtc-wb-wrapper .dingrtc-wb__media__header{align-items:center;background-color:#f5f5f5;border-top-left-radius:3px;border-top-right-radius:3px;box-shadow:0 0 4px 0 rgba(0,0,0,.2);cursor:pointer;display:flex;font-weight:500;height:30px;justify-content:space-between;left:0;padding-left:10px;position:absolute;top:0;transition:all .3s ease-in-out;width:100%;z-index:1}.dingrtc-wb-wrapper .dingrtc-wb__media__body{background-color:#000;height:100%;width:100%}.dingrtc-wb-wrapper .dingrtc-wb__media__body:hover~.dingrtc-wb__media__header{visibility:visible}.dingrtc-wb-wrapper .dingrtc-wb__media__body audio,.dingrtc-wb-wrapper .dingrtc-wb__media__body video{height:100%;outline:none;pointer-events:auto;width:100%}.dingrtc-wb-wrapper .dingrtc-wb__media__body audio{background:#eff1f2}.dingrtc-wb-wrapper .dingrtc-wb__media__body audio::-webkit-media-controls-panel{background:#eff1f2;border:none}.dingrtc-wb-wrapper canvas{bottom:0;height:100%;left:0;position:absolute;right:0;top:0;width:100%;z-index:1}.dingrtc-wb-wrapper .dingrtc-wb__cache-cvs{pointer-events:none!important}.dingrtc-wb-wrapper .wb-shape-textarea{background-color:transparent;border:none;outline:none;overflow-wrap:break-word;padding:0;position:absolute;resize:none;transform-origin:0 0;white-space:pre-wrap;word-break:break-all;z-index:1}.dingrtc-wb-wrapper .wb-shape-textarea::-webkit-scrollbar{display:none}.dingrtc-wb-wrapper .dingrtc-iframe-wrapper{height:960px;left:0;position:absolute;top:0;transform-origin:0 0;width:1280px;z-index:0}.dingrtc-wb-wrapper .dingrtc-iframe-wrapper iframe{border:none;height:100%;left:0;pointer-events:auto;position:absolute;top:0;width:100%}.dingrtc-wb-wrapper .dingrtc-iframe-wrapper__blocked{position:absolute}.dingrtc-wb-wrapper .dingrtc-iframe-wrapper__blocked:after{content:\"\";height:100%;left:0;top:0;width:100%}.dingrtc-wb-tools-wrapper{pointer-events:auto}"; styleInject(css_248z); declare class RenderStats { private renderInfo; record(startTime: string, timeCost?: number): void; } declare enum RENDER_STATUS { Aavilable = 0, Busy = 1 } declare class Renderer { private wb; canvasElement: HTMLCanvasElement; cachedCanvas: HTMLCanvasElement; eraserCacheCvs: HTMLCanvasElement; constructor(wb: Whiteboard); renderStatus: RENDER_STATUS; renderStats: RenderStats; frameRenderRate: number; renderContext2d: CanvasRenderingContext2D; eraserCvsCtx: CanvasRenderingContext2D; cachedCvsCtx: CanvasRenderingContext2D; private eraserCvsOutdated; private _sizeLimitStyle; private cachedCtxSnapshot; private get translate(); private get scale(); get wbWrapperDom(): HTMLDivElement; get selectedShape(): BaseShape; get textArea(): HTMLTextAreaElement; updateCanvasSize: (autoAdjust?: boolean, force?: boolean, recheck?: boolean) => void; checkCanvasSize: () => void; hideCanvas(): void; showCanvas(): void; /** * 静态缓存shape之外的可视图形 */ private get activeShapes(); get visibleShapes(): any; get anyEraserInActiveShapes(): any; get insertType(): ShapeType; get lineWidth(): number; private getDevicePixelRatio; render: () => void; /** * 立即绘制图形 */ doRender: () => void; /** * 更新背景图和课件 */ updateBg: () => void; /** * 绘制当前页面内的活跃图形(所有图形除了静态缓存图层之外的) */ private renderActiveShapes; /** * cacheCtx 绘制的内容是否过时 */ private get isCacheCtxOutdated(); /** * 绘制当前页面内所有图形 * * 如果缓存可用,则绘制缓存图层,否则仅绘制动态图层和顶层图形 */ private renderShapes; /** * 在cache层完整绘制所有图形作为缓存, * 并清除和重绘顶层白板 */ doRebuildCacheRenderer: () => void; private rebuildCacheRenderer; /** * 渲染所有可见的形状 */ renderAllVisibleShapes(ctx: CanvasRenderingContext2D, translate: any, scale: number, forceRenderText: boolean): void; /** * 渲染顶层图形,包括镭射笔,鼠标,选中图形的外边框,选择框 */ renderTopShapes(ctx: CanvasRenderingContext2D, translate?: any, scale?: number): void; } interface IDSMsg { type: 'snapshot' | 'clear' | 'resource' | 'object'; } interface IBaseMessage extends IDSMsg { type: 'resource' | 'object'; editor: string; operationTime: number; updateTime?: number; version: number; messageSettingsDTO: { autoDelete: boolean; }; moziMessageIdDTO: { channelId: string; messageId: T; userDTO: { appId: string; userId: string; }; }; } /** * 文档资源,所有文档操作都以此同步, docId 组成 doc-{uid}-{randomid} */ interface IDocResourceMsg extends IBaseMessage { type: 'resource'; message: { resourceType: 'doc'; creator: string; curpage: string; fileKey: string; maxSeq: string; name: string; pagelist: string; docType?: DocType; url?: string; download?: string; /** * doc0-1 doc0-2 */ /** * 可选 externalDoc和标注相关字段,用于指定externalDoc和标注区域的大小 */ width?: string; /** * 可选 externalDoc和标注相关字段,用于指定externalDoc和标注区域的大小 */ height?: string; /** * 可选 pdf或滚动文档相关字段 */ pageNum?: string; /** * 可选 pdf或滚动文档相关字段 */ y?: string; }; } /** * 定义all, others, self, specific四种type和subtype,针对只clear某一页的场景需要使用specific type和对应的subtype * * self/others: 端上收到clear消息后,根据clearType和clearSubType,清除对应的对象,发给别人的一般都通过 clearedMessageIds 清除 * * 本地会使用 self/others 来减少遍历直接删除 */ interface IClearResourceMsg extends IDSMsg { type: 'clear'; channelId: string; clearSubType: 'all' | 'specific' | 'self' | 'others'; clearType: 'all' | 'specific' | 'self' | 'others'; /** * {channelId, messageId, userDTO: {appId, userId}} */ clearedMessageIds: string[]; messageType: 'resource'; resourceType: 'doc' | 'laserPointer' | 'cursor' | 'stamp' | 'vision'; operator: { appId: string; userId: string; }; } interface IClearObjMsg extends IDSMsg { type: 'clear'; channelId: string; clearSubType: 'all' | 'specific' | 'self' | 'others'; clearType: 'all' | 'specific' | 'self' | 'others'; /** * {channelId, messageId, userDTO: {appId, userId}} */ clearedMessageIds: string[]; messageType: 'object'; operator: { appId: string; userId: string; }; } type ConnectionInfo = { sessionId: string; userId: string; userName: string; pid: string; appId: string; token: string; channelId: string; gslb: string; securityToken: string; }; declare abstract class ISession extends EventEmitter<{ 'data-received': (data: string, from: string, isBroadcast: boolean) => void; 'cmd-received': (from_pid: string, cmdType: CmdDataType, cmd: string, data: string, broadcast: boolean, reqId?: number | undefined) => void; 'status-sync': () => void; 'user-join': (userId: string) => void; 'user-leave': (userId: string) => void; }> { private clearCursorTimer?; abstract get isConnected(): boolean; abstract get connectionInfo(): ConnectionInfo; abstract sendData(data: string, sendBack: boolean, broadcast: boolean, to?: string): void; generateBaseMessage(messageId: string, autoDelete: boolean, creatorUserId: string): IBaseMessage; /** * 发送文档资源消息 * @param doc 文档资源 * @param curPage 可选,如果改变当前页面,传入指定页面 * @param pages 可选,如果有页面增删,传入增删后的页面列表 * @returns */ sendDocResourceMessage(doc: BaseDoc, curPage?: string, pages?: string[]): void; /** * 发送文档资源消息 */ sendCreateDocResourceMessage(docId: string, pages: number, name: string, width?: number, height?: number): void; /** * 发送 pdf 文档资源消息 */ sendCreatePdfDocResourceMessage(docId: string, name: string, url: string, fileKey?: string): void; /** * 发送文档激活(切换到某个文档)消息 */ sendActiveDocResourceMessage(docId: string): void; /** * 发送图形绘制消息 */ sendShapeDrawMessage(shape: BaseShape): void; /** * 发送图形形变消息 */ sendShapeRgnMessage(shape: BaseShape): void; /** * 发送激光笔资源 */ sendLaserPointerMsg(x: number, y: number): void; /** * 发送图章资源缓存消息 */ sendStampMsg(id: string, url: string, resizable: boolean): void; /** * 发送鼠标位置同步消息 */ sendCursorMsg(x: number, y: number, color: string, type: MouseType): void; /** * 发送视角同步消息 */ sendVisionResourceMsg(width: number, height: number, minx: number, miny: number): void; /** * 发送清除资源消息 */ sendClearResourceMsg(resourceType: 'doc' | 'laserPointer' | 'cursor' | 'vision', ids: string[]): void; /** * 发送清除绘制内容消息 */ sendClearDrawMsg(ids: { seq: string; userId: string; }[]): void; } /** * 自定义文档 */ declare class ExternalDoc extends BaseDoc { static DOC_TYPE: DocType; externalDocWidth: number; externalDocHeight: number; get width(): number; get type(): DocType; get sharePageSize(): boolean; get canModifyPage(): boolean; constructor(docInfo: { docId: string; name: string; creator: string; curPageId: string; pageVersion: number; fileKey?: string; browseMode: DocBrowserMode; width: number; height: number; }); } declare class DocManager extends EventEmitter<{ requestRender: () => any; /** * 文档切换、页码切换,或者缩放、平移事件都会导致viewprot 更新 */ 'viewport-updated': () => any; 'page-index-changed': (activeDocId: string, pageIndex: number, totalPages: number) => void; 'doc-created': (docId: string) => void; 'doc-deleted': (docId: string) => void; 'doc-switched': () => void; 'doc-load-failed': (docId: string, docName: string) => void; }> { private browseMode; private docs; private _activeDocId; /** * 切换当前激活的文档 * @param docId */ switchActiveDoc(docId: string): void; get activeDocId(): string; get activeDoc(): any; /** * 设置文档浏览模式,flip为翻页模式, scroll 为滚动模式 * * scroll 模式的一些限制: 不允许从中间删除删除页码,只可以从最后一页新建页码 * @param mode */ setBrowserMode(mode: DocBrowserMode, disableScale?: boolean, defaultDocPages?: number, defaultDocPageSize?: { width: number; height: number; }): void; private onDocRequestRender; private onViewportUpdate; private onPageIndexChanged; addDoc(doc: BaseDoc): void; deleteDoc(doc: BaseDoc): void; deleteDocByDocId(docId: string): void; getDocByDocId(docId: string): any; getDocByPageId(pageId: string): any; getDocs(): BaseDoc[]; constructor(); private setup; handleDocCommnad(cmd: IDocResourceMsg, isSendByMe: boolean, wrapperDomRect: IDomRect, sizeConfig?: { width: number; height: number; limited: boolean; }): void; private handlePdfResource; /** * pdf doc文档居中显示 */ private centerPdfDoc; private updateDocFromCommand; private createDocFromCommand; reset(): void; } declare abstract class Whiteboard extends EventEmitter { sessionId: string; static PdfPlugin?: PdfPlugin; /** * 使用pdf插件 * @params plugin */ static usePdf(plugin: PdfPlugin): void; static MAX_SCALE: number; static MIN_SCALE: number; static MAX_MEDIA_SIZE: number; static DEFAULE_DOC_URL_DURATION: number; protected static RENDER_INTEVAL: number; protected static CMD_SEND_WAIT: number; static sdkVersion: string; static docTranscodeStaicMaxSize: number; isOpen: boolean; private _everOpened; protected bSharingVision: boolean; protected _lockVisonUserId: string; _prevPenetrable: boolean; lastMediaStates: { id: string; is_play: boolean; muted: boolean; pos: number; time: number; }[]; protected connection?: ISession; protected cwSnapshotCbMap: Map any>; private stampId?; /** * 手写板缩放倍率,默认情况下手写板1:1缩放到屏幕 */ tabletScale: number; /** * 手写板和画布的匹配模式,默认保证宽度匹配 */ tabletMatchMode: 'fitWidth' | 'fitHeight'; /** * 手写板相对画布的位移,不受缩放影响 */ tabletTranslate: [number, number]; isWhiteboardOpen: boolean; _penetrable: boolean; protected _cursorSyncEnabled: boolean; sizeLimitVisible: boolean; /** * 移动画布时,手写板书写出现在画板的位置是否受影响。 * static: 跟随画布移动; * sticky: 不随画布移动 */ tabletWriteMode: 'static' | 'sticky'; protected _innerEventhub: EventEmitter<{ sessionReady: () => void; syncCompleted: () => void; pageSwitched: () => void; 'doc-switched': (docId: string) => void; roleChanged: (data: { eventId: string; result: number; }) => void; }>; private pinchShapeCenter; private lastPanMoveDelta; private pinchBoardOriginalScale; private wheelDsiabled; private frameRenderRateInterval; protected wrapperDomRect?: DOMRect; bgImg: HTMLImageElement; textArea: HTMLTextAreaElement; private renderFPS; wbWrapperDom: HTMLDivElement; pdfWrapper: HTMLDivElement; private insertingShape?; private hammer; private metricsBuffer; private sendMetricsTimeout?; private clearLaserPointerId?; private panMoveType; protected natureObjSeq: number; selectIndicator: SelectIndicator; eraserIndicator: EraserIndicator; private _shiftPressing; /** * 画布默认大小 */ sizeConfig?: { width: number; height: number; limited: boolean; }; /** * 禁止手势缩放和移动画布 */ private _scaleAndMoveDisabled; /** * 图形是否可见 */ isShapesVisible: boolean; laserPointers: LaserPointer[]; cursors: Cursor[]; protected _visionLockInfo?: { width: number; height: number; minx: number; miny: number; userId: string; }; private pinchEndTime; scrollToScale: boolean; _bFollowVision: boolean; docManager: DocManager; private _cursorSyncType; private originalTranslate; private originalDragStartPonit; protected renderer: Renderer; private failoverShapeCache; private failoverDocCache; get isSynchronizer(): boolean; /** * 获取画布容器的位置信息 */ protected getWrapperDomRect(): IDomRect; get history(): any; get userId(): string; get appId(): string; get channelId(): string; get token(): string; get userName(): string; get cid(): string; get activeDoc(): any; get activeDocId(): string; get isSizeLimited(): boolean; protected get pages(): any; abstract get isConnected(): boolean; /** * 画笔颜色,对新绘制的 shape 生效 */ strokeStyle: string; /** * 填充颜色,对新绘制的 shape 生效 */ fillStyle: string; /** * 新绘制的 shape 的填充类型,填充颜色或者不填充 */ fillType: ShapeFillType; /** * 画笔宽度,对新绘制 shape 生效 */ private _lineWidth; get lineWidth(): number; set lineWidth(value: number); /** * 是否绘制虚线 */ dashed: boolean; /** * 文字是否斜体,对新插入的文本生效 */ italic: boolean; /** * 文字是否加粗,对新插入的文本生效 */ bold: boolean; /** * 字体大小,对插入的文本生效 */ private _fontSize; get fontSize(): number; set fontSize(value: number); /** * 画布缩放适应背景图的模式 */ bgScaleMode: ImageScalingMode; protected _role: WBRoleType; /** * 获取当前用户的角色 */ get role(): WBRoleType; /** * 当前用户是否是 admin 用户 */ get isAdmin(): boolean; get currentPage(): any; /** * 获取当前白板视图的缩放比例 */ get scale(): number; set scale(nextScale: number); protected _hookShapeRenderRequest(shape: BaseShape): void; getCursorSyncType(): "write" | "all"; setCursorSyncType(type: 'write' | 'all'): void; /** * 设置白板角色类型 * @param roleType 角色类型 * @param force 是否是failover时设置角色 */ setRoleType(roleType: WBRoleType): void; private insertType; /** * 获取当前的工具类型 */ getToolType(): ShapeType; /** * 设置工具类型 * @param insertType 工具类型 */ setToolType(insertType: ShapeType): void; private checkDocAndSetPenetrable; protected getDevicePixelRatio(): number; /** * 列举出所有的文档信息 */ enumerateDocs(): { docId: string; name: string; creator: string; currentPage: number; fileKey: string; }[]; private multiSelecetedShapes; private _selectedShape?; /** * 当前被选中的 shape */ get selectedShape(): BaseShape | undefined; /** * 设置或清除当前选择的 shape */ set selectedShape(shape: BaseShape | undefined); /** * 设置当前选中 shape 的 style * @param style */ setSelectedShapeStyle(style: { lineWidth?: number; strokeStyle?: string; fillStyle?: string; fillType?: string; }): void; /** * 设置当前选中 shape 的 fontStyle * @param fontStyle */ setSelectedShapeFontStyle(style: { italic?: boolean; bold?: boolean; fontSize?: number; }): void; get pageIndex(): any; /** * 切换白板文件 * @param docId */ switchToDoc(docId: string): void; /** * 获取当前页码 */ getCurrentPageNumber(): any; /** * 跳转到指定页码 (从 0 开始) * @param pageIndex 页码 * @param docId 文档 id,默认操作当前文档 * @param autoSwitchTo 是否自动切换到该文档 */ gotoPage(pageIndex: number, docId?: string, autoSwitchToDoc?: boolean): void; private gotoPdfPage; /** * 切换到下一页 */ nextPage(): void; /** * 切换到上一页 */ prevPage(): void; /** * 获取当前白板视图的背景颜色 */ get backgroundColor(): string; /** * 设置当前白板视图的背景颜色(仅支持 rgba颜色,如: rgba(0,0,0,0.7)) */ set backgroundColor(color: string); /** * 获取总白板页码数 */ getTotalNumberOfPages(): any; get visibleShapes(): any; get translate(): any; /** * 获取画板当前在水平和竖直方向的位移 */ getTranslate(): { x: any; y: any; }; /** * 设置画板偏移 * @param x 水平方向偏移 * @param y 竖直方向偏移 (如果是pdf view,只能垂直方向移动) * @param smooth 是否平滑移动 * @param duration 平滑移动时间,默认 400 ms */ setTranslate(x: number, y: number, smooth?: boolean, duration?: number): void; /** * 获取当前视角下最大的可见的横坐标取值 */ private getVisionMaxX; private getVisionMaxY; private onHistoryChanged; private onActiveDocSwitched; private onActivePageChanged; private setUpHistoryListener; /** * 撤消上一次操作 */ undo(): void; /** * 重做白板的上一次被撤销操作 */ redo(): void; /** * * @param shapeId 要恢复状态的 shapeID * @param actionType shape 最近一次操作的动作 * @param lastState 要恢复到的 state, 如果 actionType 是 HistoryActionType.newShape 则不用传 */ private restoreShapeFormSavedState; /** * 通过 id 获取 shape */ getShapeById(id: string): any; /** * 清理白板状态,恢复到初始状态 */ reset(): void; /** * 设置白板背景图缩放模式 * @param mode 背景图缩放模式 */ setBackgroundImageScalingMode(scaleMode: ImageScalingMode): void; private getShapeStyle; /** * 限制图片最大宽度, * 当有sizeConfig限制时,以sizeConfig位置,否则最多 2048 * @param img * @param docId 跟进 docId 判断是否需要考虑 sizeConfig 限定图片大小 */ _getLimitedImgSize(width: number, height: number): { imgWidth: number; imgHeight: number; }; /** * 缩放 page 里的每一页到fit传入的长宽 * @param page * @param bgWidth * @param bgHeight * @param scaleMode */ _scaleBoardFitBackground(doc: BaseDoc): void; /** * 根据 sizeConfig 缩放相关页面 */ protected fitWithSizeConfig(): void; /** * 设置背景图片 * @param url 背景图片 url * @param scaleMode 画布缩放贴合背景图片的模式 */ setBackgroundImage(url: string): any; protected updateBgImgPosition(backgroundImage: Image, imgWidth: number, imgHeight: number): void; /** * 添加图片到白板中 * @param url 背景图片 url */ addImageShape(url: string): Promise; setStamp(stampId: string): void; /** * 返回当前白板页的缩略图 */ get thumbnails(): any; protected setMediaShapeCallback(shape: MediaShape): void; /** * 添加音频文件到白板中 * @param url 音频文件 url */ addAudioShape(url: string): Promise; /** * 添加视频到白板中 * @param url 视频 url */ addVideoShape(url: string): Promise; private setAsSelectedShape; /** * 添加一个新页面到指定位置 * @param pageIndex 指定位置 * @param autoSwitch 是否自动切换到新页面 * @param docId 文档 id,默认操作当前文档 * @param autoSwitchTo 是否自动切换到该文档 */ insertPage(pageIndex: number, autoSwitch?: boolean, docId?: string, autoSwitchToDoc?: boolean): any; /** * 添加一个新页面到最后 * @param autoSwitch 是否自动切换到新页面 */ addPage: (autoSwitch?: boolean) => any; /** * 删除指定页面 * @param index 页码 * @param docId 文档 id,默认操作当前文档 */ removePage: (index?: number, docId?: string) => void; /** * 滚动模式下删除某页时删除此页的所有图形 */ private removeScrollDocShapesByScrollY; /** * 设置是否显示限制大小区域的边界 * @param visible * @param style */ setSizeLimitVisible(visible: boolean): void; /** * 在页面scroll和window resize 时自动更新画布大小 */ protected autoUpdateCanvasSize: any; /** * 手动调用更新画布 size(一般用于在外部画布容器变化后,主动调用更新画板大小信息) * @param autoAdjust 是否自动调整画布内容 * @param keepScale 自动调整画布内容时是否保持缩放比例 */ updateCanvasSize: (autoAdjust?: boolean, keepScale?: boolean, recheck?: boolean) => void; /** * 更新自定义透明文档位置 */ protected updateCustomDocPosition(doc: ExternalDoc): void; /** * pdf doc文档居中显示 */ protected centerPdfDoc(doc?: BaseDoc): void; /** * 检测当前滚动位置,显示周围几张PDF图片 */ protected lazyLoadPdfPage: any; /** * 检测当前展示位置,如果当前位置的pfd未渲染,则开始渲染当前页面 */ protected lazyRenderPdfPage: any; protected getPdfVisiblePage(): { pagesNum: number; start: number; end: number; firstVisibleIndex: number; lastVisibleIndex: number; }; protected followVision(vision: { width: number; height: number; minx: number; miny: number; }): void; /** * 计算在当前画布大小下,居中显示某个视角时,画布的scale和translate值 */ protected calculateScaleAndTranslate(visionInfo: { width: number; height: number; minx: number; miny: number; }): { scale: number; translate: number[]; }; showFps(): void; stopShowFps(): void; /** * 设置白板是否穿透点击,点击穿透开启时可以透过白板直接和课件交互,例如播放课件中的媒体文件,点击课件翻页等 */ setPenetrable(nextPenetrable: boolean): void; /** * 获取当前视窗的坐标范围 */ getViewport(page?: any, canvasDomRect?: IDomRect): { minx: number; miny: number; maxx: number; maxy: number; }; /** * 隐藏白板上绘制的轨迹,所有的轨迹都会隐藏,可以控制是否隐藏背景图 * @param hideBackgroundImg 是否隐藏背景图 */ setShapesVisible(enabled: boolean, hideBackgroundImg?: boolean): void; protected render: () => void; /** * 触摸或点击点位转换成缩放和平移后的坐标 * @param p */ private convertPointCoords; /** * delta 长度缩放转换 */ private convertDelta; private checkMouseOverAndSetType; private focusTetxArea; /** * 检测文本图形是否超出边界,如果超出边界将内容调整至可见区域内 */ private chackIfTextAreaOutofBound; protected _selectShape(shape: BaseShape): void; protected _focusShape(shape: BaseShape): void; /** * 如果点位在 shpe 的四个角的 resize handle 上,返回这个 handle point,否则返回 undefined * @param x * @param y */ private getShapeResizeHandle; private rangeSelect; private clearSelectedShapes; /** * 容器大小变化后需要更新绘制内容视角的情况 */ protected get shouldUpdateViewAfterSizeChange(): boolean; protected get moveAndScaleDisabled(): boolean; private onDoubleClick; private getShapeByPoint; private onMouseDown; /** * 使白板视野回到居中位置(初始位置) */ center(doc?: any): void; enableCursorSync(): void; disableCursorSync(): void; /** * 处理选中元素的四个角上的 resize handle 的移入和移出事件 */ private onMouseMove; /** * 限定鼠标同步发送频率 */ private sendCursor; /** * 所给点位是否在任意一个多选的 shape 边框范围内 * @param x x坐标 * @param y y坐标 */ private isPointInAnyMultySlectedShape; private onPaste; protected uploadLocalImage(file: File, setAsBackground: boolean, onProgress?: (state: { total: number; loaded: number; }) => void): void; private _onPenEvent; private onMouseUp; private onTouchEnd; private onTap; private onPanStart; private batchSendRgnShapes; private onPanMove; private onPanEnd; /** * 删除批量选中的图形 */ private deleteRageSelectedShapes; private onPinchStart; private onPinch; private onPinchEnd; private onPinchMove; /** * 以 传入的点位更新当前白板页面 scale 比例,如果白板被限制大小,会自动计算出合适的 scale 和 translate * @param nextScale 要更新的 scale * @param originalX 缩放点的 x 坐标,点位是在白板 canvas 元素上的位置 * @param originalY 缩放点的 y 坐标,点位是在白板 canvas 元素上的位置 */ protected _updateBoardWithNewScale: (nextScale: number, originalX: number, originalY: number) => void; private onWheel; private throttledOnWheel; /** * 发送用户自己操作导致视图大小变化的事件 */ private emitViewportUpdateBySelfEvent; private onContextMenu; private onKeyDown; private copyShapeInfoToClipboard; private onKeyUp; private onMouseOut; /** * 禁止手势缩放面板和移动画布 */ disableScaleAndMove(): void; /** * 启用手势缩放面板和移动画布 */ enableScaleAndMove(): void; /** * 禁止通过滚轮缩放画板 */ disableWheelScale(): void; /** * 允许通过滚轮缩放画板 */ enableWheelScale(): void; protected enableInteraction(role?: WBRoleType): void; protected stopInteraction(): void; /** * 删除所传点位上的形状 */ private deleteShapeOnPosition; /** * 软删除,将 shape 设置为不可见 */ private deleteShape; /** * 截图当前白板内容 * @param autoDownload 是否自动下载,默认下载 * @param mode 截取全部或者只截取可视区域(pdf 文档只支持截取可视区域) */ snapshot(autoDownload?: boolean, mode?: 'all' | 'view', format?: 'png' | 'jpeg', quality?: number): Promise; private getNewShapeId; protected _onLoadImageError: (url: string) => void; protected isPermittedShape(shape: BaseShape): boolean; /** * 统计用户创建的图形数据 */ getStatistics(): { userId: string; shapes: { shapeStyle?: ShapeStyle; shapeId: string; visible: boolean; type: ShapeType; fontStyle?: FontStyle; text?: string; creator: string; }[]; }[]; /** * 清除某个用户绘制的内容 * @param userId 用户id * @param curPage 是否只清除当前页面 * @param clearType 要清除的类型 */ clearUserContents(userId: string, curPage: boolean, clearType: WBClearType): void; protected throttleSendLaserPointerMsg: any; constructor(sessionId?: string); /** * 创建文档 * @param totalPages 文档页数 * @param docName 文档名称 */ createDoc(totalPages: number, docName: string, width?: number, height?: number, docId?: string): void; /** * 设定语言,默认配置包含 zh_CN、zh_TW、en、de、fr、ja、ko * @param locale */ setLocale(locale: string): void; setI18nConfig(config: Record): void; getI18nConfig(): { zh_CN: { repeatPlay: string; }; de: { repeatPlay: string; }; fr: { repeatPlay: string; }; ja: { repeatPlay: string; }; ko: { repeatPlay: string; }; zh_TW: { repeatPlay: string; }; en: { repeatPlay: string; }; }; resendLocalInfoOnFailover(): void; /** * 收集本地图形数据,等待 syncCompleted 后确认哪些数据需要重新发送 */ private sendLocalDocAndShapesOnReconnect; open(wrapperEle: HTMLElement): void; /** * 关闭白板 */ close(): void; /** * 会中单次同步视角,其他端会被强制设置为与设定的视角一致(该设置仅对当前页面生效) */ alignVision(): void; /** * 设置白板视窗位置,画布会自动缩放到合适的比例,保证所选取的视窗在当前可见区域的正中央。 * 这是对白板会议的全局设置,设定后其他用户也会遵循这个配置。 * * 在指定 sizeConfig 后,默认白板新建的空白白板页也会遵循这个配置。 * (动态课件、转码文档、包含背景图的页面除外,这些版面会根据课件或背景图作合适的缩放) * @param width 视窗宽度 * @param height 视窗高度 * @param limited 白板是否限定大小 */ initVision(width: number, height: number, limited?: boolean): void; private onViewPortChanged; protected throttleSendVisionCmd: any; /** * 开启自己的视角锁定共享,将把自己的视角同步给别人 */ startVisionShare(): void; /** * 关闭自己的视角锁定,并发消息清除自己的视角resource信息 */ stopVisionShare(): void; /** * 开启视角跟随 */ startFollowVision(): void; /** * 关闭视角跟随 */ stopFollowVision(): void; /** * 删除文档 * @param docId 删除文档的 id * @param switchDocId 删除后跳转到指定文档(如果不传值,当删除的文档是当前文档时跳转至默认文档,其他文档默认不跳转) */ deleteDoc(docId: string, switchDocId?: string): void; protected throttleSendDocResourceMsg: any; /** * 清除所有用户在画布上的内容 * @param curPage 是否只清除当前页面 * @param clearType 清除类型 */ clearContents(curPage: boolean, clearType: WBClearType): void; /** * 清除某个文档的内容 * @param docId * @param clearType * @returns */ clearDocContents(docId: string, clearType: WBClearType): void; /** * 发送shape消息到server */ sendDrawCmd: (shape: BaseShape, type: "draw" | "rgn") => void; /** * 节流发送shape消息到server * * @param {BaseShape} shape * @param {string} type */ throttleSendDrawCmd: any; setScale(scale: number): void; uploadPDF(onProgress?: (state: { total: number; loaded: number; }) => void): Promise<{ url: string; fileName: string; docId: string; }>; /** * 通过 URL 添加 PDF 文档 */ addPdfDoc(url: string, name: string, docId?: string, fileKey?: string): string; /** * 文件转码 * @param target: 'png' | 'jpg' | 'pdf' * @param onUploadProgress 上传进度回调 * @param onDocTranscodeStatus 发布进度回调,支持上传进度回调,code 为4时表示发布上传进入,在code 为 3 时表示转成成功,会返回 docId,code 定义: * 0或正数表示正常状态,负数表示失败。最大支持40M文件 * 0: start upload,1: upload success,2: transcoding,3: transcode success, 4: uploading, 5: preview ready * -1: file too large, -2: upload failed, -3: transcoding failed * @param onSuccess * @param meta */ transcodeFile(params: { targetType: 'png' | 'jpg' | 'pdf'; onUploadProgress?: (state: { total: number; loaded: number; }) => void; onTranscodeProgress?: (status: 'init' | 'processing' | 'success' | 'failed') => void; }): Promise<{ pageCount: number; url: string[]; fileName: string; docId: string; }>; /** * 导入指定数量的背景图并创建一个新的文档,以这些图片作为背景 * @param urls 图片 url 列表 * @param docName 文档名称 * @param docId */ addBackgroundImages(urls: string[], docName?: string, docId?: string): void; /** * 上传音频 * @param callback 音频上传回调, 支持上传进度, code值对应状态: * -3: upload_failed, -2: err_failed_fetch_upload_token, -1: err_file_too_large, */ uploadAudio(onProgress?: (state: { total: number; loaded: number; }) => void): Promise<{ url: string; fileName: string; docId: string; }>; /** * 上传视频 * @param callback 视频上传回调, 支持上传进度, code值对应状态: * -3: upload_failed, -2: err_failed_fetch_upload_token, -1: err_file_too_large, */ uploadVideo(onProgress?: (state: { total: number; loaded: number; }) => void): Promise; private _sendMetrics; private doSendMetrics; /** * 上传图片 * @param callback 图片上传回调, 支持上传进度, code值对应状态: * -3: upload_failed, -2: err_failed_fetch_upload_token, -1: err_file_too_large, * @param setAsBackground 是否设置为背景图,默认 true */ uploadImage(setAsBackground?: boolean, onProgress?: (state: { total: number; loaded: number; }) => void): Promise; /** * 设置图章资源 */ addStamp(stampId: string, url: string, resizable: boolean): void; getSdkVersion(): string; /** * 打印白板当前的一些关键信息,用于排查问题 */ exportAsJson(saveFile?: boolean): Promise<{ snapshot: string; docsInfo: { docId: string; name: string; creator: string; pageIndex: number; pageVersion: number; pages: { pageId: string; scale: number; translate: [number, number]; backgroundColor: string; backgroundImage: ShapeReservedState; shapes: ShapeReservedState[]; }[]; fileKey: string; }[]; }>; /** * 保存日志 */ saveLogs(fileName?: string): void; } declare class WebSession extends ISession { session: DSSession; private wbManager; get sessionId(): string; get isConnected(): boolean; constructor(session: DSSession, wbManager: WhiteboardManager); get connectionInfo(): { userId: string; userName: string; channelId: string; token: string; appId: string; pid: string; securityToken: string; gslb: string; sessionId: string; }; private onReceiveUserUpdate; private onReceiveCmdData; private onReceiveData; /** * 离开该白板频道,其他用户也会收到当前用户离开的事件。 * 用于中途离开白板,对其他用户无影响。 * * 调用后当前白板实例仍然保留,可通过id获取到白板实例。 * 如果后续仍想继续使用白板,可以在获取白板实例后调用joinSession再次入会 */ leave: () => void; /** * 关闭该白板频道,其他用户也会收到频道关闭信号。 * 用于结束白板,影响所有用户。 * * 调用后当前白板实例会被清理回收掉。 */ stop: () => void; joinSession(): Promise; sendData: (command: string, sendBack?: boolean) => void; } interface WhiteboardUser { userId: string; } declare class RtcWhiteboard extends Whiteboard { wbManager: WhiteboardManager; connection: WebSession; users: WhiteboardUser[]; joinStatus: 'init' | 'joining' | 'joined' | 'leaving' | 'left'; openStatus: 'init' | 'opening' | 'opened' | 'closing' | 'closed'; constructor(connection: WebSession, wbManager: WhiteboardManager); get isConnected(): boolean; /** * 调用后当前白板实例仍然保留,可通过id获取到白板实例。 * 如果后续仍想继续使用白板,可以在获取白板实例后调用joinSession再次入会 */ leave: () => void; /** * 关闭该白板频道,其他用户也会收到频道关闭信号。 * 用于结束白板,影响所有用户。 * * 调用后当前白板实例会被清理回收掉。 */ stop: () => void; open(wrapperEle: HTMLElement): Promise; close(): void; joinSession(): Promise | Promise; protected onReceiveCommand: (command: IDSMsg) => void; private _handleSnapshotCommand; private _handleCoursorCommand; protected _handleClearResource(command: IClearResourceMsg): void; protected _handleClearObj(command: IClearObjMsg): void; private _handleStampResourceCommand; /** * 处理激光笔消息 */ private _handleLaserPointerCommand; private _handleVisionCommand; private _handleDrawCommand; } declare class WhiteboardManager extends EventEmitter { private id; private whiteboardMap; private channel; reporter: Reporter; private logger; get gslb(): string; constructor(); getWhiteboard(whiteboardId: string): RtcWhiteboard; getAnnotation(annotationId: string, sourceType: AnnotationSourceType): RtcWhiteboard; get connectionInfo(): { userId: string; userName: string; channelId: string; token: string; appId: string; pid: string; securityToken: string; gslb: string; }; detach(): void; attach(channel: DingRTCChannel): void; get isConnected(): boolean; private setupChannel; /** * 加入白板频道 * @param joinInfo * @returns */ join(joinInfo: JoinParam): Promise; /** * 离开频道,所有白板都会离开 */ leave(): void; /** * 清理本地白板缓存 */ clear(): void; /** * @override * @param event * @param args * @returns */ emit(event: T, ...args: any): boolean; } export { RtcWhiteboard, ShapeFillType, ShapeFontFormatType, ShapeLineType, ShapeOrderType, ShapeVisibleType, ShapeType as ToolType, WBClearType, Whiteboard, WhiteboardManager, WhiteboardManager as default }; export type { AnnotationSourceType, IDomRect, IWhiteboardEvents, IWhiteboardManagerEvents };