@zsviczian/excalidraw 0.17.1-obsidian-11 → 0.17.1-obsidian-12

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.
@@ -4508,10 +4508,10 @@
4508
4508
  opacity: 1;
4509
4509
  }
4510
4510
  }
4511
- /*!***********************************************************************************************************************************************************************************************************************!*\
4512
- !*** css ../../node_modules/css-loader/dist/cjs.js!../../node_modules/postcss-loader/dist/cjs.js??ruleSet[1].rules[0].use[2]!../../node_modules/sass-loader/dist/cjs.js!./components/LaserTool/LaserToolOverlay.scss ***!
4513
- \***********************************************************************************************************************************************************************************************************************/
4514
- .excalidraw .LaserToolOverlay {
4511
+ /*!*****************************************************************************************************************************************************************************************************!*\
4512
+ !*** css ../../node_modules/css-loader/dist/cjs.js!../../node_modules/postcss-loader/dist/cjs.js??ruleSet[1].rules[0].use[2]!../../node_modules/sass-loader/dist/cjs.js!./components/SVGLayer.scss ***!
4513
+ \*****************************************************************************************************************************************************************************************************/
4514
+ .excalidraw .SVGLayer {
4515
4515
  pointer-events: none;
4516
4516
  width: 100vw;
4517
4517
  height: 100vh;
@@ -4520,10 +4520,12 @@
4520
4520
  left: 0;
4521
4521
  z-index: 2;
4522
4522
  }
4523
- .excalidraw .LaserToolOverlay .LaserToolOverlayCanvas {
4523
+ .excalidraw .SVGLayer svg {
4524
4524
  image-rendering: auto;
4525
4525
  overflow: visible;
4526
4526
  position: absolute;
4527
+ width: 100%;
4528
+ height: 100%;
4527
4529
  top: 0;
4528
4530
  left: 0;
4529
4531
  }
@@ -49,7 +49,7 @@
49
49
  .excalidraw .MagicSettings .Island{height:100%;display:flex;flex-direction:column}.excalidraw .MagicSettings-confirm{padding:.5rem 1rem}.excalidraw .MagicSettings__confirm{margin-top:2rem;margin-right:auto}
50
50
  :export{themeFilter:invert(93%) hue-rotate(180deg);rightSidebarWidth:302px}.excalidraw .Modal.Dialog.ttd-dialog{padding:1.25rem}.excalidraw .Modal.Dialog.ttd-dialog.Dialog--fullscreen{margin-top:0}.excalidraw .Modal.Dialog.ttd-dialog .Island{padding-inline:0 !important;height:100%;display:flex;flex-direction:column;flex:1 1 auto;box-shadow:none}.excalidraw .Modal.Dialog.ttd-dialog .Modal__content{height:auto;max-height:100%}@media screen and (min-width: 861px){.excalidraw .Modal.Dialog.ttd-dialog .Modal__content{max-height:750px;height:100%}}.excalidraw .Modal.Dialog.ttd-dialog .Dialog__content{flex:1 1 auto}.excalidraw .ttd-dialog-desc{font-size:15px;font-style:italic;font-weight:500;margin-bottom:1.5rem}.excalidraw .ttd-dialog-tabs-root{width:100%;height:100%;display:flex;flex-direction:column}.excalidraw .ttd-dialog-tab-trigger{color:var(--color-on-surface);font-size:.875rem;margin:0;padding:0 1rem;background-color:rgba(0,0,0,0);border:0;height:2.875rem;font-weight:600;font-family:inherit;letter-spacing:.4px}.excalidraw .ttd-dialog-tab-trigger[data-state=active]{border-bottom:2px solid var(--color-primary)}.excalidraw .ttd-dialog-triggers{border-bottom:1px solid var(--color-surface-high);margin-bottom:1.5rem;padding-inline:2.5rem}.excalidraw .ttd-dialog-content{padding-inline:2.5rem;height:100%;display:flex;flex-direction:column}.excalidraw .ttd-dialog-content[hidden]{display:none}.excalidraw .ttd-dialog-input{width:auto;height:10rem;resize:none;border-radius:var(--border-radius-lg);border:1px solid var(--dialog-border-color);white-space:pre-wrap;padding:.85rem;box-sizing:border-box;font-family:monospace;text-wrap:wrap !important}@media screen and (min-width: 861px){.excalidraw .ttd-dialog-input{width:100%;height:100%}}.excalidraw .ttd-dialog-output-wrapper{display:flex;align-items:center;justify-content:center;padding:.85rem;box-sizing:border-box;flex-grow:1;position:relative;background:url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAAMUlEQVQ4T2NkYGAQYcAP3uCTZhw1gGGYhAGBZIA/nYDCgBDAm9BGDWAAJyRCgLaBCAAgXwixzAS0pgAAAABJRU5ErkJggg==) left center;border-radius:var(--border-radius-lg);border:1px solid var(--dialog-border-color);height:400px;width:auto}@media screen and (min-width: 861px){.excalidraw .ttd-dialog-output-wrapper{width:100%;height:200px}}.excalidraw .ttd-dialog-output-wrapper canvas{max-width:100%;max-height:100%}.excalidraw .ttd-dialog-output-canvas-container{display:flex;width:100%;height:100%;align-items:center;justify-content:center;flex-grow:1}.excalidraw .ttd-dialog-output-error{color:red;font-weight:800;font-size:30px;word-break:break-word;overflow:auto;max-height:100%;height:100%;width:100%;text-align:center;position:absolute;z-index:10}.excalidraw .ttd-dialog-output-error p{font-weight:500;font-family:Cascadia;text-align:left;white-space:pre-wrap;font-size:.875rem;padding:0 10px}.excalidraw .ttd-dialog-panels{height:100%}@media screen and (min-width: 861px){.excalidraw .ttd-dialog-panels{display:grid;grid-template-columns:1fr 1fr;gap:4rem}}.excalidraw .ttd-dialog-panel{display:flex;flex-direction:column;width:100%}.excalidraw .ttd-dialog-panel__header{display:flex;margin:0px 4px 4px 4px;align-items:center;gap:1rem}.excalidraw .ttd-dialog-panel__header label{font-size:14px;font-style:normal;font-weight:600}.excalidraw .ttd-dialog-panel:first-child .ttd-dialog-panel-button-container:not(.invisible){margin-bottom:4rem}@media screen and (min-width: 861px){.excalidraw .ttd-dialog-panel .ttd-dialog-panel-button-container:not(.invisible){margin-bottom:.5rem !important}}.excalidraw .ttd-dialog-panel textarea{height:100%;resize:none;border-radius:var(--border-radius-lg);border:1px solid var(--dialog-border-color);white-space:pre-wrap;padding:.85rem;box-sizing:border-box;width:100%;font-family:monospace}@media screen and (max-width: 861px){.excalidraw .ttd-dialog-panel textarea{width:auto;height:10rem}}.excalidraw .ttd-dialog-panel-button-container{margin-top:1rem;margin-bottom:.5rem}.excalidraw .ttd-dialog-panel-button-container.invisible .ttd-dialog-panel-button{display:none}@media screen and (min-width: 861px){.excalidraw .ttd-dialog-panel-button-container.invisible .ttd-dialog-panel-button{display:block;visibility:hidden}}.excalidraw .ttd-dialog-panel-button{position:relative}.excalidraw .ttd-dialog-panel-button.excalidraw-button{font-family:inherit;font-weight:600;height:2.5rem;font-size:12px;color:#fff;background-color:var(--color-primary);width:100%}.excalidraw .ttd-dialog-panel-button.excalidraw-button:hover{background-color:var(--color-primary-darker)}.excalidraw .ttd-dialog-panel-button.excalidraw-button:active{background-color:var(--color-primary-darkest)}.excalidraw .ttd-dialog-panel-button.excalidraw-button:disabled{opacity:.5;cursor:not-allowed}.excalidraw .ttd-dialog-panel-button.excalidraw-button:disabled:hover{background-color:var(--color-primary)}@media screen and (min-width: 861px){.excalidraw .ttd-dialog-panel-button.excalidraw-button{width:auto;min-width:7.5rem}}.excalidraw.theme--dark.excalidraw .ttd-dialog-panel-button.excalidraw-button{color:var(--color-gray-100)}.excalidraw .ttd-dialog-panel-button div{display:contents}.excalidraw .ttd-dialog-panel-button div.invisible{visibility:hidden}.excalidraw .ttd-dialog-panel-button div.Spinner{display:flex !important;position:absolute;inset:0;--spinner-color: white}.excalidraw.theme--dark.excalidraw .ttd-dialog-panel-button div.Spinner{--spinner-color: var(--color-gray-100)}.excalidraw .ttd-dialog-panel-button div span{padding-left:.5rem;display:flex}.excalidraw .ttd-dialog-submit-shortcut{margin-inline-start:.5rem;font-size:.625rem;opacity:.6;display:flex;gap:.125rem}.excalidraw .ttd-dialog-submit-shortcut__key{border:1px solid gray;padding:2px 3px;border-radius:4px}
51
51
  :export{themeFilter:invert(93%) hue-rotate(180deg);rightSidebarWidth:302px}.excalidraw .Toast{animation:fade-in .5s;background-color:var(--button-gray-1);border-radius:4px;bottom:10px;box-sizing:border-box;cursor:default;left:50%;margin-left:-150px;padding:4px 0;position:absolute;text-align:center;width:300px;z-index:999999}.excalidraw .Toast .Toast__message{padding:0 1.6rem;color:var(--popup-text-color);white-space:pre-wrap}.excalidraw .Toast .close{position:absolute;top:0;right:0;padding:.4rem}.excalidraw .Toast .close .ToolIcon__icon{width:1.2rem;height:1.2rem}@keyframes fade-in{from{opacity:0}to{opacity:1}}
52
- .excalidraw .LaserToolOverlay{pointer-events:none;width:100vw;height:100vh;position:fixed;top:0;left:0;z-index:2}.excalidraw .LaserToolOverlay .LaserToolOverlayCanvas{image-rendering:auto;overflow:visible;position:absolute;top:0;left:0}
52
+ .excalidraw .SVGLayer{pointer-events:none;width:100vw;height:100vh;position:fixed;top:0;left:0;z-index:2}.excalidraw .SVGLayer svg{image-rendering:auto;overflow:visible;position:absolute;width:100%;height:100%;top:0;left:0}
53
53
  .excalidraw .excalidraw-canvas-buttons{position:absolute;box-shadow:0px 2px 4px 0 rgba(0,0,0,.3);z-index:var(--zIndex-canvasButtons);background:var(--island-bg-color);border-radius:var(--border-radius-lg);display:flex;flex-direction:column;gap:.375rem}
54
54
  .excalidraw .follow-mode{position:absolute;box-sizing:border-box;pointer-events:none;border:2px solid var(--color-primary-hover);z-index:9999;display:flex;align-items:flex-end;justify-content:center}.excalidraw .follow-mode__badge{background-color:var(--color-primary-hover);color:var(--color-primary-light);padding:.25rem .5rem;margin-bottom:.5rem;border-radius:.5rem;pointer-events:all;font-size:.75rem;display:flex;gap:.5rem;align-items:center}.excalidraw .follow-mode__badge__label{display:flex;white-space:pre-wrap;line-height:1}.excalidraw .follow-mode__badge__username{display:block;white-space:nowrap;overflow:hidden;text-overflow:ellipsis;max-width:100px}.excalidraw .follow-mode__disconnect-btn{all:unset;cursor:pointer;border-radius:.25rem}.excalidraw .follow-mode__disconnect-btn:hover{background-color:var(--color-primary-darker)}.excalidraw .follow-mode__disconnect-btn:active{background-color:var(--color-primary-darkest)}.excalidraw .follow-mode__disconnect-btn svg{display:block;width:1rem;height:1rem}
55
55
  .visually-hidden{position:absolute !important;height:1px;width:1px;overflow:hidden;clip:rect(1px, 1px, 1px, 1px);white-space:nowrap;-webkit-user-select:none;user-select:none}.LoadingMessage{position:absolute;top:0;right:0;bottom:0;left:0;z-index:999;display:flex;flex-direction:column;align-items:center;justify-content:center;pointer-events:none}.LoadingMessage .Spinner{font-size:2.8em}.LoadingMessage .LoadingMessage-text{margin-top:1em;font-size:.8em}.LoadingMessage--dark{background-color:#121212;color:#ced4da}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@zsviczian/excalidraw",
3
- "version": "0.17.1-obsidian-11",
3
+ "version": "0.17.1-obsidian-12",
4
4
  "main": "main.js",
5
5
  "types": "types/excalidraw/index.d.ts",
6
6
  "files": [
@@ -45,7 +45,7 @@
45
45
  },
46
46
  "dependencies": {
47
47
  "@braintree/sanitize-url": "6.0.2",
48
- "@excalidraw/laser-pointer": "1.2.0",
48
+ "@excalidraw/laser-pointer": "1.3.1",
49
49
  "@zsviczian/mermaid-to-excalidraw": "0.2.0-obsidian-2",
50
50
  "@excalidraw/random-username": "1.1.0",
51
51
  "@radix-ui/react-popover": "1.0.3",
@@ -121,7 +121,7 @@ export declare const actionClearCanvas: {
121
121
  openDialog: {
122
122
  name: "help" | "imageExport" | "jsonExport";
123
123
  } | {
124
- name: "settings";
124
+ name: "settings"; /** zoom content to cover X of the viewport, when fitToViewport=true */
125
125
  source: "settings" | "tool" | "generation";
126
126
  tab: "text-to-diagram" | "diagram-to-code";
127
127
  } | {
@@ -285,7 +285,7 @@ export declare const actionZoomIn: {
285
285
  openDialog: {
286
286
  name: "help" | "imageExport" | "jsonExport";
287
287
  } | {
288
- name: "settings";
288
+ name: "settings"; /** zoom content to cover X of the viewport, when fitToViewport=true */
289
289
  source: "settings" | "tool" | "generation";
290
290
  tab: "text-to-diagram" | "diagram-to-code";
291
291
  } | {
@@ -479,7 +479,7 @@ export declare const actionZoomOut: {
479
479
  openDialog: {
480
480
  name: "help" | "imageExport" | "jsonExport";
481
481
  } | {
482
- name: "settings";
482
+ name: "settings"; /** zoom content to cover X of the viewport, when fitToViewport=true */
483
483
  source: "settings" | "tool" | "generation";
484
484
  tab: "text-to-diagram" | "diagram-to-code";
485
485
  } | {
@@ -673,7 +673,7 @@ export declare const actionResetZoom: {
673
673
  openDialog: {
674
674
  name: "help" | "imageExport" | "jsonExport";
675
675
  } | {
676
- name: "settings";
676
+ name: "settings"; /** zoom content to cover X of the viewport, when fitToViewport=true */
677
677
  source: "settings" | "tool" | "generation";
678
678
  tab: "text-to-diagram" | "diagram-to-code";
679
679
  } | {
@@ -867,7 +867,7 @@ export declare const zoomToFitBounds: ({ bounds, appState, fitToViewport, viewpo
867
867
  openDialog: {
868
868
  name: "help" | "imageExport" | "jsonExport";
869
869
  } | {
870
- name: "settings";
870
+ name: "settings"; /** zoom content to cover X of the viewport, when fitToViewport=true */
871
871
  source: "settings" | "tool" | "generation";
872
872
  tab: "text-to-diagram" | "diagram-to-code";
873
873
  } | {
@@ -1057,7 +1057,7 @@ export declare const zoomToFit: ({ targetElements, appState, fitToViewport, view
1057
1057
  openDialog: {
1058
1058
  name: "help" | "imageExport" | "jsonExport";
1059
1059
  } | {
1060
- name: "settings";
1060
+ name: "settings"; /** zoom content to cover X of the viewport, when fitToViewport=true */
1061
1061
  source: "settings" | "tool" | "generation";
1062
1062
  tab: "text-to-diagram" | "diagram-to-code";
1063
1063
  } | {
@@ -1245,7 +1245,7 @@ export declare const actionZoomToFitSelectionInViewport: {
1245
1245
  openDialog: {
1246
1246
  name: "help" | "imageExport" | "jsonExport";
1247
1247
  } | {
1248
- name: "settings";
1248
+ name: "settings"; /** zoom content to cover X of the viewport, when fitToViewport=true */
1249
1249
  source: "settings" | "tool" | "generation";
1250
1250
  tab: "text-to-diagram" | "diagram-to-code";
1251
1251
  } | {
@@ -1437,7 +1437,7 @@ export declare const actionZoomToFitSelection: {
1437
1437
  openDialog: {
1438
1438
  name: "help" | "imageExport" | "jsonExport";
1439
1439
  } | {
1440
- name: "settings";
1440
+ name: "settings"; /** zoom content to cover X of the viewport, when fitToViewport=true */
1441
1441
  source: "settings" | "tool" | "generation";
1442
1442
  tab: "text-to-diagram" | "diagram-to-code";
1443
1443
  } | {
@@ -1630,7 +1630,7 @@ export declare const actionZoomToFit: {
1630
1630
  openDialog: {
1631
1631
  name: "help" | "imageExport" | "jsonExport";
1632
1632
  } | {
1633
- name: "settings";
1633
+ name: "settings"; /** zoom content to cover X of the viewport, when fitToViewport=true */
1634
1634
  source: "settings" | "tool" | "generation";
1635
1635
  tab: "text-to-diagram" | "diagram-to-code";
1636
1636
  } | {
@@ -1824,7 +1824,7 @@ export declare const actionToggleTheme: {
1824
1824
  openDialog: {
1825
1825
  name: "help" | "imageExport" | "jsonExport";
1826
1826
  } | {
1827
- name: "settings";
1827
+ name: "settings"; /** zoom content to cover X of the viewport, when fitToViewport=true */
1828
1828
  source: "settings" | "tool" | "generation";
1829
1829
  tab: "text-to-diagram" | "diagram-to-code";
1830
1830
  } | {
@@ -2015,7 +2015,7 @@ export declare const actionToggleEraserTool: {
2015
2015
  openDialog: {
2016
2016
  name: "help" | "imageExport" | "jsonExport";
2017
2017
  } | {
2018
- name: "settings";
2018
+ name: "settings"; /** zoom content to cover X of the viewport, when fitToViewport=true */
2019
2019
  source: "settings" | "tool" | "generation";
2020
2020
  tab: "text-to-diagram" | "diagram-to-code";
2021
2021
  } | {
@@ -2200,7 +2200,7 @@ export declare const actionToggleHandTool: {
2200
2200
  openDialog: {
2201
2201
  name: "help" | "imageExport" | "jsonExport";
2202
2202
  } | {
2203
- name: "settings";
2203
+ name: "settings"; /** zoom content to cover X of the viewport, when fitToViewport=true */
2204
2204
  source: "settings" | "tool" | "generation";
2205
2205
  tab: "text-to-diagram" | "diagram-to-code";
2206
2206
  } | {
@@ -2386,7 +2386,7 @@ export declare const actionToggleLaserPointer: {
2386
2386
  openDialog: {
2387
2387
  name: "help" | "imageExport" | "jsonExport";
2388
2388
  } | {
2389
- name: "settings";
2389
+ name: "settings"; /** zoom content to cover X of the viewport, when fitToViewport=true */
2390
2390
  source: "settings" | "tool" | "generation";
2391
2391
  tab: "text-to-diagram" | "diagram-to-code";
2392
2392
  } | {
@@ -2568,7 +2568,7 @@ export declare const zoomToFitElements: (elements: readonly ExcalidrawElement[],
2568
2568
  openDialog: {
2569
2569
  name: "help" | "imageExport" | "jsonExport";
2570
2570
  } | {
2571
- name: "settings";
2571
+ name: "settings"; /** zoom content to cover X of the viewport, when fitToViewport=true */
2572
2572
  source: "settings" | "tool" | "generation";
2573
2573
  tab: "text-to-diagram" | "diagram-to-code";
2574
2574
  } | {
@@ -0,0 +1,33 @@
1
+ import { LaserPointerOptions } from "@excalidraw/laser-pointer";
2
+ import { AnimationFrameHandler } from "./animation-frame-handler";
3
+ import type App from "./components/App";
4
+ export interface Trail {
5
+ start(container: SVGSVGElement): void;
6
+ stop(): void;
7
+ startPath(x: number, y: number): void;
8
+ addPointToPath(x: number, y: number): void;
9
+ endPath(): void;
10
+ }
11
+ export interface AnimatedTrailOptions {
12
+ fill: (trail: AnimatedTrail) => string;
13
+ }
14
+ export declare class AnimatedTrail implements Trail {
15
+ private animationFrameHandler;
16
+ private app;
17
+ private options;
18
+ private currentTrail?;
19
+ private pastTrails;
20
+ private container?;
21
+ private trailElement;
22
+ constructor(animationFrameHandler: AnimationFrameHandler, app: App, options: Partial<LaserPointerOptions> & Partial<AnimatedTrailOptions>);
23
+ get hasCurrentTrail(): boolean;
24
+ hasLastPoint(x: number, y: number): boolean;
25
+ start(container?: SVGSVGElement): void;
26
+ stop(): void;
27
+ startPath(x: number, y: number): void;
28
+ addPointToPath(x: number, y: number): void;
29
+ endPath(): void;
30
+ private update;
31
+ private onFrame;
32
+ private drawTrail;
33
+ }
@@ -0,0 +1,16 @@
1
+ export type AnimationCallback = (timestamp: number) => void | boolean;
2
+ export type AnimationTarget = {
3
+ callback: AnimationCallback;
4
+ stopped: boolean;
5
+ };
6
+ export declare class AnimationFrameHandler {
7
+ private targets;
8
+ private rafIds;
9
+ register(key: object, callback: AnimationCallback): void;
10
+ start(key: object): void;
11
+ stop(key: object): void;
12
+ private constructFrame;
13
+ private scheduleFrame;
14
+ private cancelFrame;
15
+ private onFrame;
16
+ }
@@ -4,14 +4,16 @@ import { ActionManager } from "../actions/manager";
4
4
  import { EXPORT_IMAGE_TYPES } from "../constants";
5
5
  import { ExportedElements } from "../data";
6
6
  import { LinearElementEditor } from "../element/linearElementEditor";
7
- import { ExcalidrawElement, ExcalidrawLinearElement, NonDeleted, NonDeletedExcalidrawElement, ExcalidrawFrameLikeElement, ExcalidrawIframeElement } from "../element/types";
7
+ import { ExcalidrawElement, ExcalidrawLinearElement, NonDeleted, NonDeletedExcalidrawElement, ExcalidrawFrameLikeElement, ExcalidrawIframeElement, ExcalidrawEmbeddableElement } from "../element/types";
8
8
  import History from "../history";
9
9
  import Scene from "../scene/Scene";
10
10
  import { AppClassProperties, AppProps, AppState, ExcalidrawImperativeAPI, BinaryFiles, LibraryItems, SceneData, Device, FrameNameBoundsCache, SidebarName, SidebarTabName, ToolType, OnUserFollowedPayload } from "../types";
11
11
  import { FileSystemHandle } from "../data/filesystem";
12
12
  import { Renderer } from "../scene/Renderer";
13
- import { LaserPathManager } from "./LaserTool/LaserPathManager";
14
13
  import { Emitter } from "../emitter";
14
+ import { AnimationFrameHandler } from "../animation-frame-handler";
15
+ import { AnimatedTrail } from "../animated-trail";
16
+ import { LaserTrails } from "../laser-trails";
15
17
  export declare let showFourthFont: boolean;
16
18
  export declare const ExcalidrawContainerContext: React.Context<{
17
19
  container: HTMLDivElement | null;
@@ -60,6 +62,17 @@ declare class App extends React.Component<AppProps, AppState> {
60
62
  files: BinaryFiles;
61
63
  imageCache: AppClassProperties["imageCache"];
62
64
  private iFrameRefs;
65
+ /**
66
+ * Indicates whether the embeddable's url has been validated for rendering.
67
+ * If value not set, indicates that the validation is pending.
68
+ * Initially or on url change the flag is not reset so that we can guarantee
69
+ * the validation came from a trusted source (the editor).
70
+ **/
71
+ private embedsValidationStatus;
72
+ /** embeds that have been inserted to DOM (as a perf optim, we don't want to
73
+ * insert to DOM before user initially scrolls to them) */
74
+ private initializedEmbeds;
75
+ private elementsPendingErasure;
63
76
  hitLinkElement?: NonDeletedExcalidrawElement;
64
77
  lastPointerDownEvent: React.PointerEvent<HTMLElement> | null;
65
78
  lastPointerUpEvent: React.PointerEvent<HTMLElement> | PointerEvent | null;
@@ -69,7 +82,9 @@ declare class App extends React.Component<AppProps, AppState> {
69
82
  y: number;
70
83
  };
71
84
  allowMobileMode: boolean;
72
- laserPathManager: LaserPathManager;
85
+ animationFrameHandler: AnimationFrameHandler;
86
+ laserTrails: LaserTrails;
87
+ eraserTrail: AnimatedTrail;
73
88
  onChangeEmitter: Emitter<[elements: readonly ExcalidrawElement[], appState: AppState, files: BinaryFiles]>;
74
89
  onPointerDownEmitter: Emitter<[activeTool: {
75
90
  lastActiveTool: import("../types").ActiveTool | null;
@@ -134,12 +149,6 @@ declare class App extends React.Component<AppProps, AppState> {
134
149
  boxSelection: {
135
150
  hasOccurred: boolean;
136
151
  };
137
- elementIdsToErase: {
138
- [key: string]: {
139
- opacity: number;
140
- erase: boolean;
141
- };
142
- };
143
152
  }>, event: React.PointerEvent<HTMLElement>]>;
144
153
  onPointerUpEmitter: Emitter<[activeTool: {
145
154
  lastActiveTool: import("../types").ActiveTool | null;
@@ -204,12 +213,6 @@ declare class App extends React.Component<AppProps, AppState> {
204
213
  boxSelection: {
205
214
  hasOccurred: boolean;
206
215
  };
207
- elementIdsToErase: {
208
- [key: string]: {
209
- opacity: number;
210
- erase: boolean;
211
- };
212
- };
213
216
  }>, event: PointerEvent]>;
214
217
  onUserFollowEmitter: Emitter<[payload: OnUserFollowedPayload]>;
215
218
  onScrollChangeEmitter: Emitter<[scrollX: number, scrollY: number, zoom: Readonly<{
@@ -223,6 +226,7 @@ declare class App extends React.Component<AppProps, AppState> {
223
226
  private getHTMLIFrameElement;
224
227
  private handleEmbeddableCenterClick;
225
228
  private isIframeLikeElementCenter;
229
+ private updateEmbedValidationStatus;
226
230
  private updateEmbeddables;
227
231
  private renderEmbeddables;
228
232
  private getFrameNameDOMId;
@@ -434,7 +438,7 @@ declare class App extends React.Component<AppProps, AppState> {
434
438
  sceneX: number;
435
439
  sceneY: number;
436
440
  link: string;
437
- }) => NonDeleted<import("../element/types").ExcalidrawEmbeddableElement> | undefined;
441
+ }) => NonDeleted<ExcalidrawEmbeddableElement> | undefined;
438
442
  private createImageElement;
439
443
  private handleLinearElementOnPointerDown;
440
444
  private getCurrentItemRoundness;
@@ -0,0 +1,10 @@
1
+ import "./ToolIcon.scss";
2
+ type LaserPointerIconProps = {
3
+ title?: string;
4
+ name?: string;
5
+ checked: boolean;
6
+ onChange?(): void;
7
+ isMobile?: boolean;
8
+ };
9
+ export declare const LaserPointerButton: (props: LaserPointerIconProps) => import("react/jsx-runtime").JSX.Element;
10
+ export {};
@@ -0,0 +1,7 @@
1
+ import { Trail } from "../animated-trail";
2
+ import "./SVGLayer.scss";
3
+ type SVGLayerProps = {
4
+ trails: Trail[];
5
+ };
6
+ export declare const SVGLayer: ({ trails }: SVGLayerProps) => import("react/jsx-runtime").JSX.Element;
7
+ export {};
@@ -42,7 +42,7 @@ export declare const HelpIcon: import("react/jsx-runtime").JSX.Element;
42
42
  export declare const ExternalLinkIcon: import("react/jsx-runtime").JSX.Element;
43
43
  export declare const GithubIcon: import("react/jsx-runtime").JSX.Element;
44
44
  export declare const DiscordIcon: import("react/jsx-runtime").JSX.Element;
45
- export declare const TwitterIcon: import("react/jsx-runtime").JSX.Element;
45
+ export declare const XBrandIcon: import("react/jsx-runtime").JSX.Element;
46
46
  export declare const checkIcon: import("react/jsx-runtime").JSX.Element;
47
47
  export declare const LinkIcon: import("react/jsx-runtime").JSX.Element;
48
48
  export declare const save: import("react/jsx-runtime").JSX.Element;
@@ -1,9 +1,9 @@
1
1
  import { AppState, ExcalidrawProps, UIAppState } from "../types";
2
- import { NonDeletedExcalidrawElement } from "./types";
2
+ import { ExcalidrawEmbeddableElement, NonDeletedExcalidrawElement } from "./types";
3
3
  import { Bounds } from "./bounds";
4
4
  import "./Hyperlink.scss";
5
5
  export declare const EXTERNAL_LINK_IMG: HTMLImageElement;
6
- export declare const Hyperlink: ({ element, setAppState, onLinkOpen, setToast, }: {
6
+ export declare const Hyperlink: ({ element, setAppState, onLinkOpen, setToast, updateEmbedValidationStatus, }: {
7
7
  element: NonDeletedExcalidrawElement;
8
8
  setAppState: React.Component<any, AppState>["setState"];
9
9
  onLinkOpen: ExcalidrawProps["onLinkOpen"];
@@ -12,6 +12,7 @@ export declare const Hyperlink: ({ element, setAppState, onLinkOpen, setToast, }
12
12
  closable?: boolean;
13
13
  duration?: number;
14
14
  } | null) => void;
15
+ updateEmbedValidationStatus: (element: ExcalidrawEmbeddableElement, status: boolean) => void;
15
16
  }) => import("react/jsx-runtime").JSX.Element | null;
16
17
  export declare const actionLink: {
17
18
  name: "hyperlink";
@@ -196,5 +196,5 @@ export declare const actionSetEmbeddableAsActiveTool: {
196
196
  } & {
197
197
  keyTest?: undefined;
198
198
  };
199
- export declare const extractSrc: (htmlString: string) => string;
199
+ export declare const maybeParseEmbedSrc: (str: string) => string;
200
200
  export declare const embeddableURLValidator: (url: string | null | undefined, validateEmbeddable: ExcalidrawProps["validateEmbeddable"]) => boolean;
@@ -232,7 +232,7 @@ export declare class LinearElementEditor {
232
232
  offsetLeft: number;
233
233
  fileHandle: import("browser-fs-access").FileSystemHandle | null;
234
234
  collaborators: Map<import("../types").SocketId, Readonly<{
235
- pointer?: import("../types").CollaboratorPointer | undefined; /** indices */
235
+ pointer?: import("../types").CollaboratorPointer | undefined;
236
236
  button?: "up" | "down" | undefined;
237
237
  selectedElementIds?: Readonly<{
238
238
  [id: string]: true;
@@ -7,7 +7,6 @@ export declare const newElement: (opts: {
7
7
  } & ElementConstructorOpts) => NonDeleted<ExcalidrawGenericElement>;
8
8
  export declare const newEmbeddableElement: (opts: {
9
9
  type: "embeddable";
10
- validated: ExcalidrawEmbeddableElement["validated"];
11
10
  } & ElementConstructorOpts) => NonDeleted<ExcalidrawEmbeddableElement>;
12
11
  export declare const newIframeElement: (opts: {
13
12
  type: "iframe";
@@ -3,7 +3,6 @@ import { MaybeTransformHandleType } from "./transformHandles";
3
3
  import { AppState } from "../types";
4
4
  import { ExtractSetType } from "../utility-types";
5
5
  export declare const normalizeText: (text: string) => string;
6
- export declare const splitIntoLines: (text: string) => string[];
7
6
  export declare const redrawTextBoundingBox: (textElement: ExcalidrawTextElement, container: ExcalidrawElement | null) => void;
8
7
  export declare const bindTextToShapeAfterDuplication: (sceneElements: ExcalidrawElement[], oldElements: ExcalidrawElement[], oldIdToDuplicatedId: Map<ExcalidrawElement["id"], ExcalidrawElement["id"]>) => void;
9
8
  export declare const handleBindTextResize: (container: NonDeletedExcalidrawElement, transformHandleType: MaybeTransformHandleType, shouldMaintainAspectRatio?: boolean) => void;
@@ -76,14 +76,6 @@ export type ExcalidrawEllipseElement = _ExcalidrawElementBase & {
76
76
  };
77
77
  export type ExcalidrawEmbeddableElement = _ExcalidrawElementBase & Readonly<{
78
78
  type: "embeddable";
79
- /**
80
- * indicates whether the embeddable src (url) has been validated for rendering.
81
- * null value indicates that the validation is pending. We reset the
82
- * value on each restore (or url change) so that we can guarantee
83
- * the validation came from a trusted source (the editor). Also because we
84
- * may not have access to host-app supplied url validator during restore.
85
- */
86
- validated: boolean | null;
87
79
  scale: [number, number];
88
80
  }>;
89
81
  export type ExcalidrawIframeElement = _ExcalidrawElementBase & Readonly<{
@@ -0,0 +1,19 @@
1
+ import { AnimatedTrail, Trail } from "./animated-trail";
2
+ import { AnimationFrameHandler } from "./animation-frame-handler";
3
+ import type App from "./components/App";
4
+ export declare class LaserTrails implements Trail {
5
+ private animationFrameHandler;
6
+ private app;
7
+ localTrail: AnimatedTrail;
8
+ private collabTrails;
9
+ private container?;
10
+ constructor(animationFrameHandler: AnimationFrameHandler, app: App);
11
+ private getTrailOptions;
12
+ startPath(x: number, y: number): void;
13
+ addPointToPath(x: number, y: number): void;
14
+ endPath(): void;
15
+ start(container: SVGSVGElement): void;
16
+ stop(): void;
17
+ onFrame(): void;
18
+ private updateCollabTrails;
19
+ }
@@ -0,0 +1,3 @@
1
+ export declare const getAreaLimit: () => any;
2
+ export declare const getWidthHeightLimit: () => any;
3
+ export declare const isExcaliBrainView: () => any;
@@ -0,0 +1,14 @@
1
+ /**
2
+ * @param func handler taking at most single parameter (event).
3
+ */
4
+ export declare const withBatchedUpdates: <TFunction extends ((event: any) => void) | (() => void)>(func: Parameters<TFunction>["length"] extends 0 | 1 ? TFunction : never) => TFunction;
5
+ /**
6
+ * barches React state updates and throttles the calls to a single call per
7
+ * animation frame
8
+ */
9
+ export declare const withBatchedUpdatesThrottled: <TFunction extends ((event: any) => void) | (() => void)>(func: Parameters<TFunction>["length"] extends 0 | 1 ? TFunction : never) => {
10
+ (...args: Parameters<TFunction>): void;
11
+ flush(): void;
12
+ cancel(): void;
13
+ };
14
+ export declare const isRenderThrottlingEnabled: () => boolean;
@@ -1,8 +1,9 @@
1
- import { ExcalidrawElement, ExcalidrawTextElement, NonDeletedExcalidrawElement, ExcalidrawFreeDrawElement } from "../element/types";
1
+ import { ExcalidrawElement, ExcalidrawTextElement, NonDeletedExcalidrawElement, ExcalidrawFreeDrawElement, ExcalidrawFrameLikeElement } from "../element/types";
2
2
  import type { RoughCanvas } from "roughjs/bin/canvas";
3
3
  import type { RoughSVG } from "roughjs/bin/svg";
4
4
  import { SVGRenderConfig, StaticCanvasRenderConfig } from "../scene/types";
5
- import { AppState, StaticCanvasAppState, BinaryFiles, InteractiveCanvasAppState } from "../types";
5
+ import { AppState, StaticCanvasAppState, BinaryFiles, InteractiveCanvasAppState, ElementsPendingErasure } from "../types";
6
+ export declare const getRenderOpacity: (element: ExcalidrawElement, containingFrame: ExcalidrawFrameLikeElement | null, elementsPendingErasure: ElementsPendingErasure) => number;
6
7
  export interface ExcalidrawElementWithCanvas {
7
8
  element: ExcalidrawElement | ExcalidrawTextElement;
8
9
  canvas: HTMLCanvasElement;
@@ -1,6 +1,7 @@
1
1
  import type { Drawable, Options } from "roughjs/bin/core";
2
2
  import type { RoughGenerator } from "roughjs/bin/generator";
3
3
  import type { ExcalidrawElement, NonDeletedExcalidrawElement, ExcalidrawSelectionElement } from "../element/types";
4
+ import { EmbedsValidationStatus } from "../types";
4
5
  export declare const generateRoughOptions: (element: ExcalidrawElement, continuousPath?: boolean) => Options;
5
6
  /**
6
7
  * Generates the roughjs shape for given element.
@@ -9,7 +10,8 @@ export declare const generateRoughOptions: (element: ExcalidrawElement, continuo
9
10
  *
10
11
  * @private
11
12
  */
12
- export declare const _generateElementShape: (element: Exclude<NonDeletedExcalidrawElement, ExcalidrawSelectionElement>, generator: RoughGenerator, { isExporting, canvasBackgroundColor, }: {
13
+ export declare const _generateElementShape: (element: Exclude<NonDeletedExcalidrawElement, ExcalidrawSelectionElement>, generator: RoughGenerator, { isExporting, canvasBackgroundColor, embedsValidationStatus, }: {
13
14
  isExporting: boolean;
14
15
  canvasBackgroundColor: string;
16
+ embedsValidationStatus: EmbedsValidationStatus | null;
15
17
  }) => Drawable | Drawable[] | null;
@@ -1,7 +1,7 @@
1
1
  import { Drawable } from "roughjs/bin/core";
2
2
  import { ExcalidrawElement } from "../element/types";
3
3
  import { ElementShape, ElementShapes } from "./types";
4
- import { AppState } from "../types";
4
+ import { AppState, EmbedsValidationStatus } from "../types";
5
5
  export declare class ShapeCache {
6
6
  private static rg;
7
7
  private static cache;
@@ -20,5 +20,6 @@ export declare class ShapeCache {
20
20
  static generateElementShape: <T extends import("../element/types").ExcalidrawRectangleElement | import("../element/types").ExcalidrawDiamondElement | import("../element/types").ExcalidrawEllipseElement | import("../element/types").ExcalidrawTextElement | import("../element/types").ExcalidrawLinearElement | import("../element/types").ExcalidrawFreeDrawElement | import("../element/types").ExcalidrawImageElement | import("../element/types").ExcalidrawFrameElement | import("../element/types").ExcalidrawMagicFrameElement | import("../element/types").ExcalidrawIframeElement | import("../element/types").ExcalidrawEmbeddableElement>(element: T, renderConfig: {
21
21
  isExporting: boolean;
22
22
  canvasBackgroundColor: AppState["viewBackgroundColor"];
23
+ embedsValidationStatus: EmbedsValidationStatus;
23
24
  } | null) => ((T["type"] extends keyof ElementShapes ? ElementShapes[T["type"]] | undefined : ElementShape | undefined) & ({} | null)) | (T["type"] extends keyof ElementShapes ? ElementShapes[T["type"]] : Drawable | null);
24
25
  }
@@ -19,6 +19,9 @@ export declare const exportToSvg: (elements: readonly NonDeletedExcalidrawElemen
19
19
  frameRendering?: AppState["frameRendering"];
20
20
  frameColor?: AppState["frameColor"];
21
21
  }, files: BinaryFiles | null, opts?: {
22
+ /**
23
+ * if true, all embeddables passed in will be rendered when possible.
24
+ */
22
25
  renderEmbeddables?: boolean;
23
26
  exportingFrame?: ExcalidrawFrameLikeElement | null;
24
27
  }) => Promise<SVGSVGElement>;
@@ -1,7 +1,7 @@
1
1
  import type { RoughCanvas } from "roughjs/bin/canvas";
2
2
  import { Drawable } from "roughjs/bin/core";
3
3
  import { ExcalidrawTextElement, NonDeletedExcalidrawElement } from "../element/types";
4
- import { AppClassProperties, AppState, InteractiveCanvasAppState, StaticCanvasAppState } from "../types";
4
+ import { AppClassProperties, AppState, EmbedsValidationStatus, ElementsPendingErasure, InteractiveCanvasAppState, StaticCanvasAppState } from "../types";
5
5
  export type StaticCanvasRenderConfig = {
6
6
  canvasBackgroundColor: AppState["viewBackgroundColor"];
7
7
  imageCache: AppClassProperties["imageCache"];
@@ -9,6 +9,8 @@ export type StaticCanvasRenderConfig = {
9
9
  /** when exporting the behavior is slightly different (e.g. we can't use
10
10
  CSS filters), and we disable render optimizations for best output */
11
11
  isExporting: boolean;
12
+ embedsValidationStatus: EmbedsValidationStatus;
13
+ elementsPendingErasure: ElementsPendingErasure;
12
14
  };
13
15
  export type SVGRenderConfig = {
14
16
  offsetX: number;
@@ -19,6 +21,7 @@ export type SVGRenderConfig = {
19
21
  frameRendering: AppState["frameRendering"];
20
22
  canvasBackgroundColor: AppState["viewBackgroundColor"];
21
23
  frameColor?: AppState["frameColor"];
24
+ embedsValidationStatus: EmbedsValidationStatus;
22
25
  };
23
26
  export type InteractiveCanvasRenderConfig = {
24
27
  remoteSelectedElementIds: {
@@ -1,5 +1,5 @@
1
1
  import React from "react";
2
- import { PointerType, ExcalidrawLinearElement, NonDeletedExcalidrawElement, NonDeleted, TextAlign, ExcalidrawElement, GroupId, ExcalidrawBindableElement, Arrowhead, ChartType, FontFamilyValues, ExcalidrawTextElement, FileId, ExcalidrawImageElement, Theme, StrokeRoundness, ExcalidrawEmbeddableElement, ExcalidrawMagicFrameElement, ExcalidrawFrameLikeElement, ExcalidrawElementType } from "./element/types";
2
+ import { PointerType, ExcalidrawLinearElement, NonDeletedExcalidrawElement, NonDeleted, TextAlign, ExcalidrawElement, GroupId, ExcalidrawBindableElement, Arrowhead, ChartType, FontFamilyValues, ExcalidrawTextElement, FileId, ExcalidrawImageElement, Theme, StrokeRoundness, ExcalidrawEmbeddableElement, ExcalidrawMagicFrameElement, ExcalidrawFrameLikeElement, ExcalidrawElementType, ExcalidrawIframeLikeElement } from "./element/types";
3
3
  import { Action } from "./actions/types";
4
4
  import { Point as RoughPoint } from "roughjs/bin/geometry";
5
5
  import { LinearElementEditor } from "./element/linearElementEditor";
@@ -532,12 +532,6 @@ export type PointerDownState = Readonly<{
532
532
  boxSelection: {
533
533
  hasOccurred: boolean;
534
534
  };
535
- elementIdsToErase: {
536
- [key: ExcalidrawElement["id"]]: {
537
- opacity: ExcalidrawElement["opacity"];
538
- erase: boolean;
539
- };
540
- };
541
535
  }>;
542
536
  export type UnsubscribeCallback = () => void;
543
537
  export type ExcalidrawImperativeAPI = {
@@ -617,4 +611,6 @@ export type KeyboardModifiersObject = {
617
611
  };
618
612
  export type Primitive = number | string | boolean | bigint | symbol | null | undefined;
619
613
  export type JSONValue = string | number | boolean | null | object;
614
+ export type EmbedsValidationStatus = Map<ExcalidrawIframeLikeElement["id"], boolean>;
615
+ export type ElementsPendingErasure = Set<ExcalidrawElement["id"]>;
620
616
  export {};
@@ -141,19 +141,6 @@ export type ResolvablePromise<T> = Promise<T> & {
141
141
  reject: (error: Error) => void;
142
142
  };
143
143
  export declare const resolvablePromise: <T>() => ResolvablePromise<T>;
144
- /**
145
- * @param func handler taking at most single parameter (event).
146
- */
147
- export declare const withBatchedUpdates: <TFunction extends ((event: any) => void) | (() => void)>(func: Parameters<TFunction>["length"] extends 0 | 1 ? TFunction : never) => TFunction;
148
- /**
149
- * barches React state updates and throttles the calls to a single call per
150
- * animation frame
151
- */
152
- export declare const withBatchedUpdatesThrottled: <TFunction extends ((event: any) => void) | (() => void)>(func: Parameters<TFunction>["length"] extends 0 | 1 ? TFunction : never) => {
153
- (...args: Parameters<TFunction>): void;
154
- flush(): void;
155
- cancel(): void;
156
- };
157
144
  export declare const nFormatter: (num: number, digits: number) => string;
158
145
  export declare const getVersion: () => string;
159
146
  export declare const supportsEmoji: () => boolean;
@@ -205,7 +192,6 @@ export declare const assertNever: (value: never, message: string | null, softAss
205
192
  export declare const memoize: <T extends Record<string, any>, R extends unknown>(func: (opts: T) => R) => ((opts: T) => R) & {
206
193
  clear: () => void;
207
194
  };
208
- export declare const isRenderThrottlingEnabled: () => boolean;
209
195
  /** Checks if value is inside given collection. Useful for type-safety. */
210
196
  export declare const isMemberOf: <T extends string>(collection: Set<T> | Record<T, any> | Map<T, any> | readonly T[], value: string) => value is T;
211
197
  export declare const cloneJSON: <T>(obj: T) => T;
@@ -217,3 +203,5 @@ export declare function addEventListener<K extends keyof DocumentEventMap>(targe
217
203
  export declare function addEventListener(target: Document, type: string, listener: (this: Document, ev: Event) => any, options?: boolean | AddEventListenerOptions): UnsubscribeCallback;
218
204
  export declare function addEventListener<K extends keyof FontFaceSetEventMap>(target: FontFaceSet, type: K, listener: (this: FontFaceSet, ev: FontFaceSetEventMap[K]) => any, options?: boolean | AddEventListenerOptions): UnsubscribeCallback;
219
205
  export declare function addEventListener<K extends keyof HTMLElementEventMap>(target: Document | (Window & typeof globalThis) | HTMLElement | undefined | null | false, type: K, listener: (this: HTMLDivElement, ev: HTMLElementEventMap[K]) => any, options?: boolean | AddEventListenerOptions): UnsubscribeCallback;
206
+ export declare function getSvgPathFromStroke(points: number[][], closed?: boolean): string;
207
+ export declare const normalizeEOL: (str: string) => string;