@tldraw/editor 5.4.0-next.ef99ab47e5ce → 5.5.0-canary.078a77321dc3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist-cjs/index.d.ts +119 -49
- package/dist-cjs/index.js +4 -1
- package/dist-cjs/index.js.map +2 -2
- package/dist-cjs/lib/TldrawEditor.js +7 -2
- package/dist-cjs/lib/TldrawEditor.js.map +2 -2
- package/dist-cjs/lib/components/MenuClickCapture.js +6 -8
- package/dist-cjs/lib/components/MenuClickCapture.js.map +2 -2
- package/dist-cjs/lib/components/default-components/CanvasOverlays.js +1 -3
- package/dist-cjs/lib/components/default-components/CanvasOverlays.js.map +2 -2
- package/dist-cjs/lib/components/default-components/DefaultErrorFallback.js +1 -1
- package/dist-cjs/lib/components/default-components/DefaultErrorFallback.js.map +1 -1
- package/dist-cjs/lib/config/TLUserPreferences.js +6 -2
- package/dist-cjs/lib/config/TLUserPreferences.js.map +2 -2
- package/dist-cjs/lib/config/createTLStore.js +1 -1
- package/dist-cjs/lib/config/createTLStore.js.map +2 -2
- package/dist-cjs/lib/constants.js +2 -0
- package/dist-cjs/lib/constants.js.map +2 -2
- package/dist-cjs/lib/editor/Editor.js +190 -300
- package/dist-cjs/lib/editor/Editor.js.map +2 -2
- package/dist-cjs/lib/editor/derivations/shapeIdsInCurrentPage.js +7 -3
- package/dist-cjs/lib/editor/derivations/shapeIdsInCurrentPage.js.map +2 -2
- package/dist-cjs/lib/editor/managers/ClickManager/ClickManager.js +3 -3
- package/dist-cjs/lib/editor/managers/ClickManager/ClickManager.js.map +2 -2
- package/dist-cjs/lib/editor/managers/CollaboratorsManager/CollaboratorsManager.js +8 -8
- package/dist-cjs/lib/editor/managers/CollaboratorsManager/CollaboratorsManager.js.map +2 -2
- package/dist-cjs/lib/editor/managers/EdgeScrollManager/EdgeScrollManager.js +10 -6
- package/dist-cjs/lib/editor/managers/EdgeScrollManager/EdgeScrollManager.js.map +2 -2
- package/dist-cjs/lib/editor/managers/FontManager/FontManager.js +2 -1
- package/dist-cjs/lib/editor/managers/FontManager/FontManager.js.map +2 -2
- package/dist-cjs/lib/editor/managers/InputsManager/InputsManager.js +79 -6
- package/dist-cjs/lib/editor/managers/InputsManager/InputsManager.js.map +2 -2
- package/dist-cjs/lib/editor/managers/ScribbleManager/ScribbleManager.js +7 -0
- package/dist-cjs/lib/editor/managers/ScribbleManager/ScribbleManager.js.map +2 -2
- package/dist-cjs/lib/editor/managers/SnapManager/BoundsSnaps.js +0 -2
- package/dist-cjs/lib/editor/managers/SnapManager/BoundsSnaps.js.map +2 -2
- package/dist-cjs/lib/editor/managers/TextManager/TextManager.js +1 -2
- package/dist-cjs/lib/editor/managers/TextManager/TextManager.js.map +2 -2
- package/dist-cjs/lib/editor/managers/ThemeManager/ThemeManager.js +7 -3
- package/dist-cjs/lib/editor/managers/ThemeManager/ThemeManager.js.map +2 -2
- package/dist-cjs/lib/editor/managers/TickManager/TickManager.js +6 -3
- package/dist-cjs/lib/editor/managers/TickManager/TickManager.js.map +2 -2
- package/dist-cjs/lib/editor/managers/UserPreferencesManager/UserPreferencesManager.js +12 -1
- package/dist-cjs/lib/editor/managers/UserPreferencesManager/UserPreferencesManager.js.map +2 -2
- package/dist-cjs/lib/editor/overlays/OverlayManager.js +3 -7
- package/dist-cjs/lib/editor/overlays/OverlayManager.js.map +2 -2
- package/dist-cjs/lib/editor/overlays/strokeShapeIndicators.js +0 -1
- package/dist-cjs/lib/editor/overlays/strokeShapeIndicators.js.map +2 -2
- package/dist-cjs/lib/editor/shapes/BaseFrameLikeShapeUtil.js +3 -1
- package/dist-cjs/lib/editor/shapes/BaseFrameLikeShapeUtil.js.map +2 -2
- package/dist-cjs/lib/editor/shapes/shared/getPerfectDashProps.js +1 -0
- package/dist-cjs/lib/editor/shapes/shared/getPerfectDashProps.js.map +2 -2
- package/dist-cjs/lib/editor/tools/BaseBoxShapeTool/children/Pointing.js +1 -1
- package/dist-cjs/lib/editor/tools/BaseBoxShapeTool/children/Pointing.js.map +2 -2
- package/dist-cjs/lib/editor/tools/StateNode.js +3 -2
- package/dist-cjs/lib/editor/tools/StateNode.js.map +2 -2
- package/dist-cjs/lib/globals/editors.js +57 -0
- package/dist-cjs/lib/globals/editors.js.map +7 -0
- package/dist-cjs/lib/globals/menus.js +9 -4
- package/dist-cjs/lib/globals/menus.js.map +2 -2
- package/dist-cjs/lib/hooks/useCanvasEvents.js +2 -0
- package/dist-cjs/lib/hooks/useCanvasEvents.js.map +2 -2
- package/dist-cjs/lib/hooks/useDocumentEvents.js +39 -9
- package/dist-cjs/lib/hooks/useDocumentEvents.js.map +2 -2
- package/dist-cjs/lib/hooks/useLocalStore.js +10 -6
- package/dist-cjs/lib/hooks/useLocalStore.js.map +2 -2
- package/dist-cjs/lib/hooks/usePassThroughWheelEvents.js +1 -0
- package/dist-cjs/lib/hooks/usePassThroughWheelEvents.js.map +2 -2
- package/dist-cjs/lib/hooks/usePeerIds.js +2 -1
- package/dist-cjs/lib/hooks/usePeerIds.js.map +2 -2
- package/dist-cjs/lib/license/LicenseManager.js +9 -2
- package/dist-cjs/lib/license/LicenseManager.js.map +2 -2
- package/dist-cjs/lib/license/LicenseProvider.js +16 -3
- package/dist-cjs/lib/license/LicenseProvider.js.map +2 -2
- package/dist-cjs/lib/license/useLicenseManagerState.js +5 -4
- package/dist-cjs/lib/license/useLicenseManagerState.js.map +2 -2
- package/dist-cjs/lib/primitives/Box.js +2 -1
- package/dist-cjs/lib/primitives/Box.js.map +2 -2
- package/dist-cjs/lib/primitives/Vec.js +4 -3
- package/dist-cjs/lib/primitives/Vec.js.map +2 -2
- package/dist-cjs/lib/primitives/geometry/Arc2d.js +1 -1
- package/dist-cjs/lib/primitives/geometry/Arc2d.js.map +2 -2
- package/dist-cjs/lib/primitives/geometry/CubicBezier2d.js +1 -1
- package/dist-cjs/lib/primitives/geometry/CubicBezier2d.js.map +2 -2
- package/dist-cjs/lib/primitives/geometry/Edge2d.js +1 -1
- package/dist-cjs/lib/primitives/geometry/Edge2d.js.map +2 -2
- package/dist-cjs/lib/primitives/geometry/Group2d.js +71 -26
- package/dist-cjs/lib/primitives/geometry/Group2d.js.map +2 -2
- package/dist-cjs/lib/primitives/geometry/Point2d.js +1 -1
- package/dist-cjs/lib/primitives/geometry/Point2d.js.map +2 -2
- package/dist-cjs/lib/primitives/utils.js +2 -1
- package/dist-cjs/lib/primitives/utils.js.map +2 -2
- package/dist-cjs/lib/utils/deepLinks.js +5 -1
- package/dist-cjs/lib/utils/deepLinks.js.map +2 -2
- package/dist-cjs/lib/utils/normalizeWheel.js +2 -0
- package/dist-cjs/lib/utils/normalizeWheel.js.map +2 -2
- package/dist-cjs/lib/utils/rotation.js +1 -9
- package/dist-cjs/lib/utils/rotation.js.map +2 -2
- package/dist-cjs/lib/utils/sync/TLLocalSyncClient.js +17 -0
- package/dist-cjs/lib/utils/sync/TLLocalSyncClient.js.map +2 -2
- package/dist-cjs/lib/utils/sync/alerts.js +1 -1
- package/dist-cjs/lib/utils/sync/alerts.js.map +1 -1
- package/dist-cjs/version.js +3 -3
- package/dist-cjs/version.js.map +1 -1
- package/dist-esm/index.d.mts +119 -49
- package/dist-esm/index.mjs +9 -2
- package/dist-esm/index.mjs.map +2 -2
- package/dist-esm/lib/TldrawEditor.mjs +9 -4
- package/dist-esm/lib/TldrawEditor.mjs.map +2 -2
- package/dist-esm/lib/components/MenuClickCapture.mjs +6 -8
- package/dist-esm/lib/components/MenuClickCapture.mjs.map +2 -2
- package/dist-esm/lib/components/default-components/CanvasOverlays.mjs +1 -3
- package/dist-esm/lib/components/default-components/CanvasOverlays.mjs.map +2 -2
- package/dist-esm/lib/components/default-components/DefaultErrorFallback.mjs +1 -1
- package/dist-esm/lib/components/default-components/DefaultErrorFallback.mjs.map +1 -1
- package/dist-esm/lib/config/TLUserPreferences.mjs +6 -2
- package/dist-esm/lib/config/TLUserPreferences.mjs.map +2 -2
- package/dist-esm/lib/config/createTLStore.mjs +1 -1
- package/dist-esm/lib/config/createTLStore.mjs.map +2 -2
- package/dist-esm/lib/constants.mjs +2 -0
- package/dist-esm/lib/constants.mjs.map +2 -2
- package/dist-esm/lib/editor/Editor.mjs +199 -301
- package/dist-esm/lib/editor/Editor.mjs.map +2 -2
- package/dist-esm/lib/editor/derivations/shapeIdsInCurrentPage.mjs +7 -3
- package/dist-esm/lib/editor/derivations/shapeIdsInCurrentPage.mjs.map +2 -2
- package/dist-esm/lib/editor/managers/ClickManager/ClickManager.mjs +3 -3
- package/dist-esm/lib/editor/managers/ClickManager/ClickManager.mjs.map +2 -2
- package/dist-esm/lib/editor/managers/CollaboratorsManager/CollaboratorsManager.mjs +9 -9
- package/dist-esm/lib/editor/managers/CollaboratorsManager/CollaboratorsManager.mjs.map +2 -2
- package/dist-esm/lib/editor/managers/EdgeScrollManager/EdgeScrollManager.mjs +10 -6
- package/dist-esm/lib/editor/managers/EdgeScrollManager/EdgeScrollManager.mjs.map +2 -2
- package/dist-esm/lib/editor/managers/FontManager/FontManager.mjs +2 -1
- package/dist-esm/lib/editor/managers/FontManager/FontManager.mjs.map +2 -2
- package/dist-esm/lib/editor/managers/InputsManager/InputsManager.mjs +81 -8
- package/dist-esm/lib/editor/managers/InputsManager/InputsManager.mjs.map +2 -2
- package/dist-esm/lib/editor/managers/ScribbleManager/ScribbleManager.mjs +7 -0
- package/dist-esm/lib/editor/managers/ScribbleManager/ScribbleManager.mjs.map +2 -2
- package/dist-esm/lib/editor/managers/SnapManager/BoundsSnaps.mjs +0 -2
- package/dist-esm/lib/editor/managers/SnapManager/BoundsSnaps.mjs.map +2 -2
- package/dist-esm/lib/editor/managers/TextManager/TextManager.mjs +2 -3
- package/dist-esm/lib/editor/managers/TextManager/TextManager.mjs.map +2 -2
- package/dist-esm/lib/editor/managers/ThemeManager/ThemeManager.mjs +7 -3
- package/dist-esm/lib/editor/managers/ThemeManager/ThemeManager.mjs.map +2 -2
- package/dist-esm/lib/editor/managers/TickManager/TickManager.mjs +6 -3
- package/dist-esm/lib/editor/managers/TickManager/TickManager.mjs.map +2 -2
- package/dist-esm/lib/editor/managers/UserPreferencesManager/UserPreferencesManager.mjs +12 -1
- package/dist-esm/lib/editor/managers/UserPreferencesManager/UserPreferencesManager.mjs.map +2 -2
- package/dist-esm/lib/editor/overlays/OverlayManager.mjs +3 -7
- package/dist-esm/lib/editor/overlays/OverlayManager.mjs.map +2 -2
- package/dist-esm/lib/editor/overlays/strokeShapeIndicators.mjs +0 -1
- package/dist-esm/lib/editor/overlays/strokeShapeIndicators.mjs.map +2 -2
- package/dist-esm/lib/editor/shapes/BaseFrameLikeShapeUtil.mjs +3 -1
- package/dist-esm/lib/editor/shapes/BaseFrameLikeShapeUtil.mjs.map +2 -2
- package/dist-esm/lib/editor/shapes/shared/getPerfectDashProps.mjs +1 -0
- package/dist-esm/lib/editor/shapes/shared/getPerfectDashProps.mjs.map +2 -2
- package/dist-esm/lib/editor/tools/BaseBoxShapeTool/children/Pointing.mjs +1 -1
- package/dist-esm/lib/editor/tools/BaseBoxShapeTool/children/Pointing.mjs.map +2 -2
- package/dist-esm/lib/editor/tools/StateNode.mjs +3 -2
- package/dist-esm/lib/editor/tools/StateNode.mjs.map +2 -2
- package/dist-esm/lib/globals/editors.mjs +37 -0
- package/dist-esm/lib/globals/editors.mjs.map +7 -0
- package/dist-esm/lib/globals/menus.mjs +9 -4
- package/dist-esm/lib/globals/menus.mjs.map +2 -2
- package/dist-esm/lib/hooks/useCanvasEvents.mjs +2 -0
- package/dist-esm/lib/hooks/useCanvasEvents.mjs.map +2 -2
- package/dist-esm/lib/hooks/useDocumentEvents.mjs +40 -10
- package/dist-esm/lib/hooks/useDocumentEvents.mjs.map +2 -2
- package/dist-esm/lib/hooks/useLocalStore.mjs +11 -7
- package/dist-esm/lib/hooks/useLocalStore.mjs.map +2 -2
- package/dist-esm/lib/hooks/usePassThroughWheelEvents.mjs +1 -0
- package/dist-esm/lib/hooks/usePassThroughWheelEvents.mjs.map +2 -2
- package/dist-esm/lib/hooks/usePeerIds.mjs +2 -1
- package/dist-esm/lib/hooks/usePeerIds.mjs.map +2 -2
- package/dist-esm/lib/license/LicenseManager.mjs +9 -2
- package/dist-esm/lib/license/LicenseManager.mjs.map +2 -2
- package/dist-esm/lib/license/LicenseProvider.mjs +16 -3
- package/dist-esm/lib/license/LicenseProvider.mjs.map +2 -2
- package/dist-esm/lib/license/useLicenseManagerState.mjs +5 -4
- package/dist-esm/lib/license/useLicenseManagerState.mjs.map +2 -2
- package/dist-esm/lib/primitives/Box.mjs +2 -1
- package/dist-esm/lib/primitives/Box.mjs.map +2 -2
- package/dist-esm/lib/primitives/Vec.mjs +4 -3
- package/dist-esm/lib/primitives/Vec.mjs.map +2 -2
- package/dist-esm/lib/primitives/geometry/Arc2d.mjs +1 -1
- package/dist-esm/lib/primitives/geometry/Arc2d.mjs.map +2 -2
- package/dist-esm/lib/primitives/geometry/CubicBezier2d.mjs +1 -1
- package/dist-esm/lib/primitives/geometry/CubicBezier2d.mjs.map +2 -2
- package/dist-esm/lib/primitives/geometry/Edge2d.mjs +1 -1
- package/dist-esm/lib/primitives/geometry/Edge2d.mjs.map +2 -2
- package/dist-esm/lib/primitives/geometry/Group2d.mjs +75 -27
- package/dist-esm/lib/primitives/geometry/Group2d.mjs.map +2 -2
- package/dist-esm/lib/primitives/geometry/Point2d.mjs +1 -1
- package/dist-esm/lib/primitives/geometry/Point2d.mjs.map +2 -2
- package/dist-esm/lib/primitives/utils.mjs +2 -1
- package/dist-esm/lib/primitives/utils.mjs.map +2 -2
- package/dist-esm/lib/utils/deepLinks.mjs +5 -1
- package/dist-esm/lib/utils/deepLinks.mjs.map +2 -2
- package/dist-esm/lib/utils/normalizeWheel.mjs +2 -0
- package/dist-esm/lib/utils/normalizeWheel.mjs.map +2 -2
- package/dist-esm/lib/utils/rotation.mjs +1 -9
- package/dist-esm/lib/utils/rotation.mjs.map +2 -2
- package/dist-esm/lib/utils/sync/TLLocalSyncClient.mjs +17 -0
- package/dist-esm/lib/utils/sync/TLLocalSyncClient.mjs.map +2 -2
- package/dist-esm/lib/utils/sync/alerts.mjs +1 -1
- package/dist-esm/lib/utils/sync/alerts.mjs.map +1 -1
- package/dist-esm/version.mjs +3 -3
- package/dist-esm/version.mjs.map +1 -1
- package/package.json +13 -7
- package/src/index.ts +6 -1
- package/src/lib/TldrawEditor.tsx +16 -4
- package/src/lib/components/MenuClickCapture.tsx +19 -18
- package/src/lib/components/default-components/CanvasOverlays.tsx +1 -3
- package/src/lib/components/default-components/DefaultErrorFallback.tsx +1 -1
- package/src/lib/config/TLUserPreferences.test.ts +18 -1
- package/src/lib/config/TLUserPreferences.ts +8 -4
- package/src/lib/config/createTLStore.ts +1 -1
- package/src/lib/constants.ts +8 -0
- package/src/lib/editor/Editor.ts +285 -392
- package/src/lib/editor/derivations/shapeIdsInCurrentPage.ts +7 -3
- package/src/lib/editor/managers/ClickManager/ClickManager.ts +5 -3
- package/src/lib/editor/managers/CollaboratorsManager/CollaboratorsManager.ts +9 -9
- package/src/lib/editor/managers/EdgeScrollManager/EdgeScrollManager.test.ts +35 -4
- package/src/lib/editor/managers/EdgeScrollManager/EdgeScrollManager.ts +13 -7
- package/src/lib/editor/managers/FontManager/FontManager.ts +2 -1
- package/src/lib/editor/managers/InputsManager/InputsManager.test.ts +199 -3
- package/src/lib/editor/managers/InputsManager/InputsManager.ts +128 -9
- package/src/lib/editor/managers/ScribbleManager/ScribbleManager.ts +12 -1
- package/src/lib/editor/managers/SnapManager/BoundsSnaps.ts +0 -2
- package/src/lib/editor/managers/TextManager/TextManager.ts +2 -6
- package/src/lib/editor/managers/ThemeManager/ThemeManager.test.ts +53 -0
- package/src/lib/editor/managers/ThemeManager/ThemeManager.ts +9 -3
- package/src/lib/editor/managers/TickManager/TickManager.test.ts +13 -0
- package/src/lib/editor/managers/TickManager/TickManager.ts +9 -3
- package/src/lib/editor/managers/UserPreferencesManager/UserPreferencesManager.test.ts +64 -3
- package/src/lib/editor/managers/UserPreferencesManager/UserPreferencesManager.ts +18 -1
- package/src/lib/editor/overlays/OverlayManager.ts +3 -7
- package/src/lib/editor/overlays/strokeShapeIndicators.ts +0 -1
- package/src/lib/editor/shapes/BaseFrameLikeShapeUtil.tsx +5 -1
- package/src/lib/editor/shapes/shared/getPerfectDashProps.ts +3 -0
- package/src/lib/editor/tools/BaseBoxShapeTool/children/Pointing.ts +4 -1
- package/src/lib/editor/tools/StateNode.test.ts +64 -0
- package/src/lib/editor/tools/StateNode.ts +12 -2
- package/src/lib/globals/editors.test.ts +76 -0
- package/src/lib/globals/editors.ts +53 -0
- package/src/lib/globals/menus.test.ts +33 -0
- package/src/lib/globals/menus.ts +11 -4
- package/src/lib/hooks/useCanvasEvents.ts +2 -0
- package/src/lib/hooks/useDocumentEvents.ts +60 -16
- package/src/lib/hooks/useLocalStore.ts +16 -8
- package/src/lib/hooks/usePassThroughWheelEvents.ts +3 -0
- package/src/lib/hooks/usePeerIds.ts +2 -1
- package/src/lib/license/LicenseManager.test.ts +160 -0
- package/src/lib/license/LicenseManager.ts +13 -4
- package/src/lib/license/LicenseProvider.tsx +24 -3
- package/src/lib/license/useLicenseManagerState.ts +8 -6
- package/src/lib/primitives/Box.test.ts +9 -1
- package/src/lib/primitives/Box.ts +3 -1
- package/src/lib/primitives/Vec.test.ts +10 -0
- package/src/lib/primitives/Vec.ts +4 -4
- package/src/lib/primitives/geometry/Arc2d.test.ts +235 -3
- package/src/lib/primitives/geometry/Arc2d.ts +1 -1
- package/src/lib/primitives/geometry/CubicBezier2d.test.ts +186 -3
- package/src/lib/primitives/geometry/CubicBezier2d.ts +1 -1
- package/src/lib/primitives/geometry/CubicSpline2d.test.ts +160 -3
- package/src/lib/primitives/geometry/Edge2d.test.ts +21 -3
- package/src/lib/primitives/geometry/Edge2d.ts +1 -1
- package/src/lib/primitives/geometry/Ellipse2d.test.ts +243 -3
- package/src/lib/primitives/geometry/Geometry2d.test.ts +553 -1
- package/src/lib/primitives/geometry/Group2d.test.ts +419 -3
- package/src/lib/primitives/geometry/Group2d.ts +81 -34
- package/src/lib/primitives/geometry/Point2d.test.ts +14 -3
- package/src/lib/primitives/geometry/Point2d.ts +1 -1
- package/src/lib/primitives/geometry/Polyline2d.test.ts +207 -0
- package/src/lib/primitives/geometry/Stadium2d.test.ts +191 -3
- package/src/lib/primitives/utils.test.ts +10 -1
- package/src/lib/primitives/utils.ts +4 -1
- package/src/lib/test/useCanvasEvents.test.tsx +74 -0
- package/src/lib/test/useDocumentEvents.test.tsx +107 -0
- package/src/lib/test/usePassThroughWheelEvents.test.tsx +25 -2
- package/src/lib/utils/deepLinks.test.ts +15 -0
- package/src/lib/utils/deepLinks.ts +7 -1
- package/src/lib/utils/normalizeWheel.test.ts +39 -0
- package/src/lib/utils/normalizeWheel.ts +6 -0
- package/src/lib/utils/rotation.ts +4 -12
- package/src/lib/utils/sync/TLLocalSyncClient.test.ts +56 -0
- package/src/lib/utils/sync/TLLocalSyncClient.ts +24 -0
- package/src/lib/utils/sync/alerts.ts +1 -1
- package/src/version.ts +3 -3
- package/src/lib/primitives/geometry/Polyline.test.ts +0 -5
|
@@ -53,6 +53,7 @@ var import_constants = require("../constants");
|
|
|
53
53
|
var import_domUtils = require("../exports/domUtils");
|
|
54
54
|
var import_exportToSvg = require("../exports/exportToSvg");
|
|
55
55
|
var import_getSvgAsImage = require("../exports/getSvgAsImage");
|
|
56
|
+
var import_editors = require("../globals/editors");
|
|
56
57
|
var import_menus = require("../globals/menus");
|
|
57
58
|
var import_time = require("../globals/time");
|
|
58
59
|
var import_options = require("../options");
|
|
@@ -256,6 +257,10 @@ class Editor extends import_eventemitter3.default {
|
|
|
256
257
|
if (!nextPageState) nextPageState = { ...prevPageState };
|
|
257
258
|
nextPageState.editingShapeId = null;
|
|
258
259
|
}
|
|
260
|
+
if (prevPageState.croppingShapeId && shapesNoLongerInPage.has(prevPageState.croppingShapeId)) {
|
|
261
|
+
if (!nextPageState) nextPageState = { ...prevPageState };
|
|
262
|
+
nextPageState.croppingShapeId = null;
|
|
263
|
+
}
|
|
259
264
|
const hintingShapeIds = prevPageState.hintingShapeIds.filter(
|
|
260
265
|
(id) => !shapesNoLongerInPage.has(id)
|
|
261
266
|
);
|
|
@@ -498,10 +503,11 @@ class Editor extends import_eventemitter3.default {
|
|
|
498
503
|
this.cancelDoubleClick();
|
|
499
504
|
}
|
|
500
505
|
if (prev?.selectedShapeIds !== next?.selectedShapeIds) {
|
|
506
|
+
const selectedShapeIds = new Set(next.selectedShapeIds);
|
|
501
507
|
const filtered = next.selectedShapeIds.filter((id) => {
|
|
502
508
|
let parentId = this.getShape(id)?.parentId;
|
|
503
509
|
while ((0, import_tlschema.isShapeId)(parentId)) {
|
|
504
|
-
if (
|
|
510
|
+
if (selectedShapeIds.has(parentId)) {
|
|
505
511
|
return false;
|
|
506
512
|
}
|
|
507
513
|
parentId = this.getShape(parentId)?.parentId;
|
|
@@ -571,9 +577,11 @@ class Editor extends import_eventemitter3.default {
|
|
|
571
577
|
this.on("tick", this._flushEventsForTick);
|
|
572
578
|
this.on("mount", () => {
|
|
573
579
|
this._isMounted.set(true);
|
|
580
|
+
(0, import_editors.registerMountedEditor)(this);
|
|
574
581
|
});
|
|
575
582
|
this.on("unmount", () => {
|
|
576
583
|
this._isMounted.set(false);
|
|
584
|
+
(0, import_editors.unregisterMountedEditor)(this);
|
|
577
585
|
});
|
|
578
586
|
this.timers.requestAnimationFrame(() => {
|
|
579
587
|
this._tickManager.start();
|
|
@@ -583,7 +591,10 @@ class Editor extends import_eventemitter3.default {
|
|
|
583
591
|
const mode = this.store.props.collaboration.mode;
|
|
584
592
|
this.disposables.add(
|
|
585
593
|
(0, import_state.react)("update collaboration mode", () => {
|
|
586
|
-
|
|
594
|
+
const isReadonly = mode.get() === "readonly";
|
|
595
|
+
(0, import_state.unsafe__withoutCapture)(
|
|
596
|
+
() => this._updateInstanceState({ isReadonly }, { history: "ignore" })
|
|
597
|
+
);
|
|
587
598
|
})
|
|
588
599
|
);
|
|
589
600
|
}
|
|
@@ -613,6 +624,14 @@ class Editor extends import_eventemitter3.default {
|
|
|
613
624
|
);
|
|
614
625
|
}
|
|
615
626
|
options;
|
|
627
|
+
/**
|
|
628
|
+
* The license manager whose feature flags apply to this editor. Assigned by `<TldrawEditor />`
|
|
629
|
+
* when it creates the editor, so that UI rendered outside the editor tree can resolve the
|
|
630
|
+
* editor's license through the editor instance. Undefined for editors created directly.
|
|
631
|
+
*
|
|
632
|
+
* @internal
|
|
633
|
+
*/
|
|
634
|
+
licenseManager;
|
|
616
635
|
contextId = (0, import_utils.uniqueId)();
|
|
617
636
|
/**
|
|
618
637
|
* The editor's store
|
|
@@ -807,6 +826,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
807
826
|
if (this._isMounted.get()) {
|
|
808
827
|
this.emit("unmount");
|
|
809
828
|
}
|
|
829
|
+
(0, import_editors.unregisterMountedEditor)(this);
|
|
810
830
|
this.stopCameraAnimation();
|
|
811
831
|
if (this.getInstanceState().followingUserId) {
|
|
812
832
|
this.stopFollowingUser();
|
|
@@ -932,7 +952,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
932
952
|
getShapeUtil(arg) {
|
|
933
953
|
const type = typeof arg === "string" ? arg : arg.type;
|
|
934
954
|
const shapeUtil = (0, import_utils.getOwnProperty)(this.shapeUtils, type);
|
|
935
|
-
|
|
955
|
+
if (!shapeUtil) throw new Error(`No shape util found for type "${type}"`);
|
|
936
956
|
return shapeUtil;
|
|
937
957
|
}
|
|
938
958
|
hasShapeUtil(arg) {
|
|
@@ -1597,7 +1617,8 @@ class Editor extends import_eventemitter3.default {
|
|
|
1597
1617
|
if (direction === "next" || direction === "prev") {
|
|
1598
1618
|
const shapeIds = readingOrderShapes.map((shape2) => shape2.id);
|
|
1599
1619
|
const currentIndex = currentShapeId ? shapeIds.indexOf(currentShapeId) : -1;
|
|
1600
|
-
const
|
|
1620
|
+
const startIndex = currentIndex === -1 && direction === "prev" ? 0 : currentIndex;
|
|
1621
|
+
const adjacentIndex = (startIndex + (direction === "next" ? 1 : -1) + shapeIds.length) % shapeIds.length;
|
|
1601
1622
|
adjacentShapeId = shapeIds[adjacentIndex];
|
|
1602
1623
|
} else {
|
|
1603
1624
|
if (!currentShapeId) return;
|
|
@@ -1721,7 +1742,9 @@ class Editor extends import_eventemitter3.default {
|
|
|
1721
1742
|
const selectedShapes = this.getSelectedShapes();
|
|
1722
1743
|
if (!selectedShapes.length) return;
|
|
1723
1744
|
const selectedShape = selectedShapes[0];
|
|
1724
|
-
const children =
|
|
1745
|
+
const children = (0, import_utils.compact)(
|
|
1746
|
+
this.getSortedChildIdsForParent(selectedShape.id).map((id) => this.getShape(id))
|
|
1747
|
+
);
|
|
1725
1748
|
const sortedChildren = this._getShapesInReadingOrder(children);
|
|
1726
1749
|
if (sortedChildren.length === 0) return;
|
|
1727
1750
|
this._selectShapesAndZoom([sortedChildren[0].id]);
|
|
@@ -1788,18 +1811,13 @@ class Editor extends import_eventemitter3.default {
|
|
|
1788
1811
|
* @internal
|
|
1789
1812
|
*/
|
|
1790
1813
|
getShapesSharedRotation(shapeIds) {
|
|
1791
|
-
let foundFirst = false;
|
|
1792
1814
|
let rotation = 0;
|
|
1793
1815
|
for (let i = 0, n = shapeIds.length; i < n; i++) {
|
|
1794
|
-
const
|
|
1795
|
-
if (
|
|
1796
|
-
|
|
1797
|
-
|
|
1798
|
-
|
|
1799
|
-
}
|
|
1800
|
-
} else {
|
|
1801
|
-
foundFirst = true;
|
|
1802
|
-
rotation = pageTransform.rotation();
|
|
1816
|
+
const pageRotation = this.getShapePageTransform(shapeIds[i]).rotation();
|
|
1817
|
+
if (i === 0) {
|
|
1818
|
+
rotation = pageRotation;
|
|
1819
|
+
} else if (pageRotation !== rotation) {
|
|
1820
|
+
return 0;
|
|
1803
1821
|
}
|
|
1804
1822
|
}
|
|
1805
1823
|
return rotation;
|
|
@@ -1825,11 +1843,9 @@ class Editor extends import_eventemitter3.default {
|
|
|
1825
1843
|
return bounds;
|
|
1826
1844
|
}
|
|
1827
1845
|
const boxFromRotatedVertices = import_Box.Box.FromPoints(
|
|
1828
|
-
shapeIds.flatMap(
|
|
1829
|
-
|
|
1830
|
-
|
|
1831
|
-
return pageTransform.applyToPoints(this.getShapeGeometry(id).bounds.corners);
|
|
1832
|
-
}).map((p) => p.rot(-selectionRotation))
|
|
1846
|
+
shapeIds.flatMap(
|
|
1847
|
+
(id) => this.getShapePageTransform(id).applyToPoints(this.getShapeGeometry(id).bounds.corners)
|
|
1848
|
+
).map((p) => p.rot(-selectionRotation))
|
|
1833
1849
|
);
|
|
1834
1850
|
boxFromRotatedVertices.point = boxFromRotatedVertices.point.rot(selectionRotation);
|
|
1835
1851
|
return boxFromRotatedVertices;
|
|
@@ -1840,9 +1856,14 @@ class Editor extends import_eventemitter3.default {
|
|
|
1840
1856
|
getSelectionRotatedScreenBounds() {
|
|
1841
1857
|
const bounds = this.getSelectionRotatedPageBounds();
|
|
1842
1858
|
if (!bounds) return void 0;
|
|
1843
|
-
const
|
|
1844
|
-
const zoom = this.
|
|
1845
|
-
return new import_Box.Box(
|
|
1859
|
+
const screenBounds = this.getViewportScreenBounds();
|
|
1860
|
+
const { x: cx, y: cy, z: zoom } = this.getCamera();
|
|
1861
|
+
return new import_Box.Box(
|
|
1862
|
+
(bounds.x + cx) * zoom + screenBounds.x,
|
|
1863
|
+
(bounds.y + cy) * zoom + screenBounds.y,
|
|
1864
|
+
bounds.width * zoom,
|
|
1865
|
+
bounds.height * zoom
|
|
1866
|
+
);
|
|
1846
1867
|
}
|
|
1847
1868
|
getFocusedGroupId() {
|
|
1848
1869
|
return this.getCurrentPageState().focusedGroupId ?? this.getCurrentPageId();
|
|
@@ -1943,42 +1964,28 @@ class Editor extends import_eventemitter3.default {
|
|
|
1943
1964
|
*/
|
|
1944
1965
|
setEditingShape(shape) {
|
|
1945
1966
|
const id = typeof shape === "string" ? shape : shape?.id ?? null;
|
|
1946
|
-
if (!id)
|
|
1967
|
+
if (id && !this.canEditShape(id)) return this;
|
|
1968
|
+
this.run(() => {
|
|
1969
|
+
const prevEditingShapeId = this.getEditingShapeId();
|
|
1970
|
+
if (prevEditingShapeId) {
|
|
1971
|
+
const prevEditingShape = this.getShape(prevEditingShapeId);
|
|
1972
|
+
if (prevEditingShape) {
|
|
1973
|
+
this.getShapeUtil(prevEditingShape).onEditEnd?.(prevEditingShape);
|
|
1974
|
+
}
|
|
1975
|
+
}
|
|
1947
1976
|
this.run(
|
|
1948
1977
|
() => {
|
|
1949
|
-
const prevEditingShapeId = this.getEditingShapeId();
|
|
1950
|
-
if (prevEditingShapeId) {
|
|
1951
|
-
const prevEditingShape = this.getShape(prevEditingShapeId);
|
|
1952
|
-
if (prevEditingShape) {
|
|
1953
|
-
this.getShapeUtil(prevEditingShape).onEditEnd?.(prevEditingShape);
|
|
1954
|
-
}
|
|
1955
|
-
}
|
|
1956
1978
|
this._updateCurrentPageState({ editingShapeId: null });
|
|
1957
1979
|
this._currentRichTextEditor.set(null);
|
|
1980
|
+
if (!id) return;
|
|
1981
|
+
this.select(id);
|
|
1982
|
+
this._updateCurrentPageState({ editingShapeId: id });
|
|
1983
|
+
const nextEditingShape = this.getShape(id);
|
|
1984
|
+
this.getShapeUtil(nextEditingShape).onEditStart?.(nextEditingShape);
|
|
1958
1985
|
},
|
|
1959
1986
|
{ history: "ignore" }
|
|
1960
1987
|
);
|
|
1961
|
-
|
|
1962
|
-
}
|
|
1963
|
-
if (!this.canEditShape(id)) return this;
|
|
1964
|
-
this.run(
|
|
1965
|
-
() => {
|
|
1966
|
-
const prevEditingShapeId = this.getEditingShapeId();
|
|
1967
|
-
if (prevEditingShapeId) {
|
|
1968
|
-
const prevEditingShape = this.getShape(prevEditingShapeId);
|
|
1969
|
-
if (prevEditingShape) {
|
|
1970
|
-
this.getShapeUtil(prevEditingShape).onEditEnd?.(prevEditingShape);
|
|
1971
|
-
}
|
|
1972
|
-
}
|
|
1973
|
-
this._updateCurrentPageState({ editingShapeId: null });
|
|
1974
|
-
this._currentRichTextEditor.set(null);
|
|
1975
|
-
this.select(id);
|
|
1976
|
-
this._updateCurrentPageState({ editingShapeId: id });
|
|
1977
|
-
const nextEditingShape = this.getShape(id);
|
|
1978
|
-
this.getShapeUtil(nextEditingShape).onEditStart?.(nextEditingShape);
|
|
1979
|
-
},
|
|
1980
|
-
{ history: "ignore" }
|
|
1981
|
-
);
|
|
1988
|
+
});
|
|
1982
1989
|
return this;
|
|
1983
1990
|
}
|
|
1984
1991
|
// Rich text editor
|
|
@@ -2084,19 +2091,12 @@ class Editor extends import_eventemitter3.default {
|
|
|
2084
2091
|
* @public
|
|
2085
2092
|
*/
|
|
2086
2093
|
setErasingShapes(shapes) {
|
|
2087
|
-
const ids = typeof shapes[0] === "string" ? shapes : shapes.map((shape) => shape.id);
|
|
2094
|
+
const ids = typeof shapes[0] === "string" ? shapes.slice() : shapes.map((shape) => shape.id);
|
|
2088
2095
|
ids.sort();
|
|
2089
2096
|
const erasingShapeIds = this.getErasingShapeIds();
|
|
2090
2097
|
this.run(
|
|
2091
2098
|
() => {
|
|
2092
|
-
if (ids
|
|
2093
|
-
for (let i = 0; i < ids.length; i++) {
|
|
2094
|
-
if (ids[i] !== erasingShapeIds[i]) {
|
|
2095
|
-
this._updateCurrentPageState({ erasingShapeIds: ids });
|
|
2096
|
-
break;
|
|
2097
|
-
}
|
|
2098
|
-
}
|
|
2099
|
-
} else {
|
|
2099
|
+
if (!(0, import_utils.areArraysShallowEqual)(ids, erasingShapeIds)) {
|
|
2100
2100
|
this._updateCurrentPageState({ erasingShapeIds: ids });
|
|
2101
2101
|
}
|
|
2102
2102
|
},
|
|
@@ -2129,6 +2129,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
2129
2129
|
if (!_shape) return false;
|
|
2130
2130
|
const util = this.getShapeUtil(_shape);
|
|
2131
2131
|
if (!util.canCrop(_shape)) return false;
|
|
2132
|
+
if (this.getIsReadonly()) return false;
|
|
2132
2133
|
if (this.isShapeOrAncestorLocked(_shape)) return false;
|
|
2133
2134
|
return true;
|
|
2134
2135
|
}
|
|
@@ -2193,11 +2194,11 @@ class Editor extends import_eventemitter3.default {
|
|
|
2193
2194
|
const collaborators = this.getCollaborators();
|
|
2194
2195
|
let leaderPresence = null;
|
|
2195
2196
|
while (targetUserId && !visited.includes(targetUserId)) {
|
|
2196
|
-
|
|
2197
|
-
|
|
2198
|
-
|
|
2199
|
-
|
|
2200
|
-
|
|
2197
|
+
const nextPresence = collaborators.find((c) => c.userId === targetUserId);
|
|
2198
|
+
if (!nextPresence) break;
|
|
2199
|
+
leaderPresence = nextPresence;
|
|
2200
|
+
targetUserId = nextPresence.followingUserId ?? null;
|
|
2201
|
+
visited.push(nextPresence.userId);
|
|
2201
2202
|
}
|
|
2202
2203
|
return leaderPresence;
|
|
2203
2204
|
}
|
|
@@ -2260,39 +2261,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
2260
2261
|
*
|
|
2261
2262
|
* @public */
|
|
2262
2263
|
getInitialZoom() {
|
|
2263
|
-
|
|
2264
|
-
if (!cameraOptions.constraints) return 1;
|
|
2265
|
-
if (cameraOptions.constraints.initialZoom === "default") return 1;
|
|
2266
|
-
const { zx, zy } = getCameraFitXFitY(this, cameraOptions);
|
|
2267
|
-
switch (cameraOptions.constraints.initialZoom) {
|
|
2268
|
-
case "fit-min": {
|
|
2269
|
-
return Math.max(zx, zy);
|
|
2270
|
-
}
|
|
2271
|
-
case "fit-max": {
|
|
2272
|
-
return Math.min(zx, zy);
|
|
2273
|
-
}
|
|
2274
|
-
case "fit-x": {
|
|
2275
|
-
return zx;
|
|
2276
|
-
}
|
|
2277
|
-
case "fit-y": {
|
|
2278
|
-
return zy;
|
|
2279
|
-
}
|
|
2280
|
-
case "fit-min-100": {
|
|
2281
|
-
return Math.min(1, Math.max(zx, zy));
|
|
2282
|
-
}
|
|
2283
|
-
case "fit-max-100": {
|
|
2284
|
-
return Math.min(1, Math.min(zx, zy));
|
|
2285
|
-
}
|
|
2286
|
-
case "fit-x-100": {
|
|
2287
|
-
return Math.min(1, zx);
|
|
2288
|
-
}
|
|
2289
|
-
case "fit-y-100": {
|
|
2290
|
-
return Math.min(1, zy);
|
|
2291
|
-
}
|
|
2292
|
-
default: {
|
|
2293
|
-
throw (0, import_utils.exhaustiveSwitchError)(cameraOptions.constraints.initialZoom);
|
|
2294
|
-
}
|
|
2295
|
-
}
|
|
2264
|
+
return this._getFitZoom(this.getCameraOptions().constraints?.initialZoom ?? "default");
|
|
2296
2265
|
}
|
|
2297
2266
|
/**
|
|
2298
2267
|
* Get the camera's base level for calculating actual zoom levels based on the zoom steps.
|
|
@@ -2304,11 +2273,13 @@ class Editor extends import_eventemitter3.default {
|
|
|
2304
2273
|
*
|
|
2305
2274
|
* @public */
|
|
2306
2275
|
getBaseZoom() {
|
|
2276
|
+
return this._getFitZoom(this.getCameraOptions().constraints?.baseZoom ?? "default");
|
|
2277
|
+
}
|
|
2278
|
+
_getFitZoom(fit) {
|
|
2307
2279
|
const cameraOptions = this.getCameraOptions();
|
|
2308
|
-
if (!cameraOptions.constraints) return 1;
|
|
2309
|
-
if (cameraOptions.constraints.baseZoom === "default") return 1;
|
|
2280
|
+
if (!cameraOptions.constraints || fit === "default") return 1;
|
|
2310
2281
|
const { zx, zy } = getCameraFitXFitY(this, cameraOptions);
|
|
2311
|
-
switch (
|
|
2282
|
+
switch (fit) {
|
|
2312
2283
|
case "fit-min": {
|
|
2313
2284
|
return Math.max(zx, zy);
|
|
2314
2285
|
}
|
|
@@ -2334,7 +2305,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
2334
2305
|
return Math.min(1, zy);
|
|
2335
2306
|
}
|
|
2336
2307
|
default: {
|
|
2337
|
-
throw (0, import_utils.exhaustiveSwitchError)(
|
|
2308
|
+
throw (0, import_utils.exhaustiveSwitchError)(fit);
|
|
2338
2309
|
}
|
|
2339
2310
|
}
|
|
2340
2311
|
}
|
|
@@ -2368,7 +2339,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
2368
2339
|
...this._cameraOptions.__unsafe__getWithoutCapture(),
|
|
2369
2340
|
...opts
|
|
2370
2341
|
});
|
|
2371
|
-
if (next.zoomSteps
|
|
2342
|
+
if (!next.zoomSteps || next.zoomSteps.length < 1) next.zoomSteps = [1];
|
|
2372
2343
|
this._cameraOptions.set(next);
|
|
2373
2344
|
this.setCamera(this.getCamera());
|
|
2374
2345
|
return this;
|
|
@@ -2389,8 +2360,8 @@ class Editor extends import_eventemitter3.default {
|
|
|
2389
2360
|
const vsb = this.getViewportScreenBounds();
|
|
2390
2361
|
if (cameraOptions.constraints) {
|
|
2391
2362
|
const { constraints } = cameraOptions;
|
|
2392
|
-
const
|
|
2393
|
-
const
|
|
2363
|
+
const px = Math.min(constraints.padding.x, vsb.w / 2);
|
|
2364
|
+
const py = Math.min(constraints.padding.y, vsb.h / 2);
|
|
2394
2365
|
const bounds = import_Box.Box.From(cameraOptions.constraints.bounds);
|
|
2395
2366
|
const zx = (vsb.w - px * 2) / bounds.w;
|
|
2396
2367
|
const zy = (vsb.h - py * 2) / bounds.h;
|
|
@@ -2429,12 +2400,12 @@ class Editor extends import_eventemitter3.default {
|
|
|
2429
2400
|
break;
|
|
2430
2401
|
}
|
|
2431
2402
|
case "inside": {
|
|
2432
|
-
if (z < zx) x = (0, import_utils2.clamp)(x, minX, (vsb.w - px) / z - bounds.w);
|
|
2403
|
+
if (z < zx) x = (0, import_utils2.clamp)(x, minX, (vsb.w - px) / z - bounds.w - bounds.x);
|
|
2433
2404
|
else x = (0, import_utils2.clamp)(x, minX + freeW, minX);
|
|
2434
2405
|
break;
|
|
2435
2406
|
}
|
|
2436
2407
|
case "outside": {
|
|
2437
|
-
x = (0, import_utils2.clamp)(x, px / z - bounds.w, (vsb.w - px) / z);
|
|
2408
|
+
x = (0, import_utils2.clamp)(x, px / z - bounds.w - bounds.x, (vsb.w - px) / z - bounds.x);
|
|
2438
2409
|
break;
|
|
2439
2410
|
}
|
|
2440
2411
|
case "free": {
|
|
@@ -2455,12 +2426,12 @@ class Editor extends import_eventemitter3.default {
|
|
|
2455
2426
|
break;
|
|
2456
2427
|
}
|
|
2457
2428
|
case "inside": {
|
|
2458
|
-
if (z < zy) y = (0, import_utils2.clamp)(y, minY, (vsb.h - py) / z - bounds.h);
|
|
2429
|
+
if (z < zy) y = (0, import_utils2.clamp)(y, minY, (vsb.h - py) / z - bounds.h - bounds.y);
|
|
2459
2430
|
else y = (0, import_utils2.clamp)(y, minY + freeH, minY);
|
|
2460
2431
|
break;
|
|
2461
2432
|
}
|
|
2462
2433
|
case "outside": {
|
|
2463
|
-
y = (0, import_utils2.clamp)(y, py / z - bounds.h, (vsb.h - py) / z);
|
|
2434
|
+
y = (0, import_utils2.clamp)(y, py / z - bounds.h - bounds.y, (vsb.h - py) / z - bounds.y);
|
|
2464
2435
|
break;
|
|
2465
2436
|
}
|
|
2466
2437
|
case "free": {
|
|
@@ -2527,14 +2498,16 @@ class Editor extends import_eventemitter3.default {
|
|
|
2527
2498
|
setCamera(point, opts) {
|
|
2528
2499
|
const { isLocked } = this._cameraOptions.__unsafe__getWithoutCapture();
|
|
2529
2500
|
if (isLocked && !opts?.force) return this;
|
|
2501
|
+
const _point = import_Vec.Vec.Cast(point);
|
|
2502
|
+
if (!Number.isFinite(_point.x) || !Number.isFinite(_point.y) || !Number.isFinite(_point.z)) {
|
|
2503
|
+
throw Error(
|
|
2504
|
+
`Editor.setCamera: expected finite values, got (${_point.x}, ${_point.y}, ${_point.z}).`
|
|
2505
|
+
);
|
|
2506
|
+
}
|
|
2530
2507
|
this.stopCameraAnimation();
|
|
2531
2508
|
if (this.getInstanceState().followingUserId) {
|
|
2532
2509
|
this.stopFollowingUser();
|
|
2533
2510
|
}
|
|
2534
|
-
const _point = import_Vec.Vec.Cast(point);
|
|
2535
|
-
if (!Number.isFinite(_point.x)) _point.x = 0;
|
|
2536
|
-
if (!Number.isFinite(_point.y)) _point.y = 0;
|
|
2537
|
-
if (_point.z === void 0 || !Number.isFinite(_point.z)) point.z = this.getZoomLevel();
|
|
2538
2511
|
const camera = this.getConstrainedCamera(_point, opts);
|
|
2539
2512
|
if (opts?.animation) {
|
|
2540
2513
|
const { width, height } = this.getViewportScreenBounds();
|
|
@@ -2828,9 +2801,9 @@ class Editor extends import_eventemitter3.default {
|
|
|
2828
2801
|
}
|
|
2829
2802
|
const remaining = duration - elapsed;
|
|
2830
2803
|
const t = easing(1 - remaining / duration);
|
|
2831
|
-
const left = start.minX
|
|
2832
|
-
const top = start.minY
|
|
2833
|
-
const right = start.maxX
|
|
2804
|
+
const left = (0, import_utils.lerp)(start.minX, end.minX, t);
|
|
2805
|
+
const top = (0, import_utils.lerp)(start.minY, end.minY, t);
|
|
2806
|
+
const right = (0, import_utils.lerp)(start.maxX, end.maxX, t);
|
|
2834
2807
|
this._setCamera(new import_Vec.Vec(-left, -top, this.getViewportScreenBounds().width / (right - left)), {
|
|
2835
2808
|
force: true
|
|
2836
2809
|
});
|
|
@@ -2908,12 +2881,12 @@ class Editor extends import_eventemitter3.default {
|
|
|
2908
2881
|
let newCy = cy + dy;
|
|
2909
2882
|
let newCz = cz;
|
|
2910
2883
|
if (dirZ !== 0) {
|
|
2911
|
-
newCz = cz * (
|
|
2884
|
+
newCz = cz * Math.exp(dirZ * currentSpeed * elapsed);
|
|
2912
2885
|
const center = this.getViewportScreenCenter();
|
|
2913
2886
|
newCx += center.x / newCz - center.x / cz;
|
|
2914
2887
|
newCy += center.y / newCz - center.y / cz;
|
|
2915
2888
|
}
|
|
2916
|
-
currentSpeed *= 1 - friction;
|
|
2889
|
+
currentSpeed *= (1 - friction) ** (elapsed / import_constants.FRAME_MS_60HZ);
|
|
2917
2890
|
if (currentSpeed < speedThreshold) {
|
|
2918
2891
|
cancel();
|
|
2919
2892
|
} else {
|
|
@@ -3346,12 +3319,12 @@ class Editor extends import_eventemitter3.default {
|
|
|
3346
3319
|
const renderingShapes = [];
|
|
3347
3320
|
let nextIndex = this.options.maxShapesPerPage * 2;
|
|
3348
3321
|
let nextBackgroundIndex = this.options.maxShapesPerPage;
|
|
3349
|
-
const erasingShapeIds = this.getErasingShapeIds();
|
|
3322
|
+
const erasingShapeIds = new Set(this.getErasingShapeIds());
|
|
3350
3323
|
const addShapeById = (id, opacity, isAncestorErasing) => {
|
|
3351
3324
|
const shape = this.getShape(id);
|
|
3352
3325
|
if (!shape) return;
|
|
3353
3326
|
if (this.isShapeHidden(shape)) {
|
|
3354
|
-
const isErasing = isAncestorErasing || erasingShapeIds.
|
|
3327
|
+
const isErasing = isAncestorErasing || erasingShapeIds.has(id);
|
|
3355
3328
|
for (const childId of this.getSortedChildIdsForParent(id)) {
|
|
3356
3329
|
addShapeById(childId, opacity, isErasing);
|
|
3357
3330
|
}
|
|
@@ -3361,7 +3334,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
3361
3334
|
let isShapeErasing = false;
|
|
3362
3335
|
const util = this.getShapeUtil(shape);
|
|
3363
3336
|
if (useEditorState) {
|
|
3364
|
-
isShapeErasing = !isAncestorErasing && erasingShapeIds.
|
|
3337
|
+
isShapeErasing = !isAncestorErasing && erasingShapeIds.has(id);
|
|
3365
3338
|
if (isShapeErasing) {
|
|
3366
3339
|
opacity *= 0.32;
|
|
3367
3340
|
}
|
|
@@ -3953,10 +3926,8 @@ class Editor extends import_eventemitter3.default {
|
|
|
3953
3926
|
}
|
|
3954
3927
|
_getShapePageBoundsCache() {
|
|
3955
3928
|
return this.store.createComputedCache("pageBoundsCache", (shape) => {
|
|
3956
|
-
const pageTransform = this.getShapePageTransform(shape);
|
|
3957
|
-
if (!pageTransform) return void 0;
|
|
3958
3929
|
return import_Box.Box.FromPoints(
|
|
3959
|
-
|
|
3930
|
+
this.getShapePageTransform(shape).applyToPoints(this.getShapeGeometry(shape).boundsVertices)
|
|
3960
3931
|
);
|
|
3961
3932
|
});
|
|
3962
3933
|
}
|
|
@@ -4074,7 +4045,9 @@ class Editor extends import_eventemitter3.default {
|
|
|
4074
4045
|
if (pageMask) {
|
|
4075
4046
|
if (pageMask.length === 0) return void 0;
|
|
4076
4047
|
const { corners } = pageBounds;
|
|
4077
|
-
if (corners.every((p, i) =>
|
|
4048
|
+
if (pageMask.length === corners.length && corners.every((p, i) => import_Vec.Vec.Equals(p, pageMask[i]))) {
|
|
4049
|
+
return pageBounds.clone();
|
|
4050
|
+
}
|
|
4078
4051
|
const intersection = (0, import_intersect.intersectPolygonPolygon)(pageMask, corners);
|
|
4079
4052
|
if (!intersection) return;
|
|
4080
4053
|
return import_Box.Box.FromPoints(intersection);
|
|
@@ -4298,23 +4271,22 @@ class Editor extends import_eventemitter3.default {
|
|
|
4298
4271
|
let inMarginClosestToEdgeHit = null;
|
|
4299
4272
|
const searchMargin = Math.max(innerMargin, outerMargin, this.getHitTestMargin());
|
|
4300
4273
|
const candidateIds = this._spatialIndex.getShapeIdsAtPoint(point, searchMargin);
|
|
4301
|
-
const shapesToCheck =
|
|
4302
|
-
if (!candidateIds.has(shape.id) && !this.isShapeFrameLike(shape)) return false;
|
|
4303
|
-
if (shape.isLocked && !hitLocked || this.isShapeHidden(shape) || this.isShapeOfType(shape, "group"))
|
|
4304
|
-
return false;
|
|
4305
|
-
const pageMask = this.getShapeMask(shape);
|
|
4306
|
-
if (pageMask && !(0, import_utils2.pointInPolygon)(point, pageMask)) return false;
|
|
4307
|
-
if (filter && !filter(shape)) return false;
|
|
4308
|
-
return true;
|
|
4309
|
-
});
|
|
4274
|
+
const shapesToCheck = opts.renderingOnly ? this.getCurrentPageRenderingShapesSorted() : this.getCurrentPageShapesSorted();
|
|
4310
4275
|
for (let i = shapesToCheck.length - 1; i >= 0; i--) {
|
|
4311
4276
|
const shape = shapesToCheck[i];
|
|
4277
|
+
if (!candidateIds.has(shape.id) && !this.isShapeFrameLike(shape)) continue;
|
|
4278
|
+
if (shape.isLocked && !hitLocked || this.isShapeHidden(shape) || this.isShapeOfType(shape, "group")) {
|
|
4279
|
+
continue;
|
|
4280
|
+
}
|
|
4281
|
+
const pageMask = this.getShapeMask(shape);
|
|
4282
|
+
if (pageMask && !(0, import_utils2.pointInPolygon)(point, pageMask)) continue;
|
|
4283
|
+
if (filter && !filter(shape)) continue;
|
|
4312
4284
|
const geometry = this.getShapeGeometry(shape);
|
|
4313
4285
|
const isGroup = geometry instanceof import_Group2d.Group2d;
|
|
4314
4286
|
const pointInShapeSpace = this.getPointInShapeSpace(shape, point);
|
|
4315
4287
|
const shapeUtil = this.getShapeUtil(shape);
|
|
4316
4288
|
const isShapeFrameLike = this.isShapeFrameLike(shape);
|
|
4317
|
-
if (isShapeFrameLike || (this.isShapeOfType(shape, "note") || this.isShapeOfType(shape, "arrow") || this.isShapeOfType(shape, "geo") && shape.props.fill === "none") && shapeUtil.getText(shape)?.trim()) {
|
|
4289
|
+
if (isGroup && (isShapeFrameLike || (this.isShapeOfType(shape, "note") || this.isShapeOfType(shape, "arrow") || this.isShapeOfType(shape, "geo") && shape.props.fill === "none") && shapeUtil.getText(shape)?.trim())) {
|
|
4318
4290
|
for (const childGeometry of geometry.children) {
|
|
4319
4291
|
if (childGeometry.isLabel && childGeometry.isPointInBounds(pointInShapeSpace)) {
|
|
4320
4292
|
return shape;
|
|
@@ -4413,11 +4385,15 @@ class Editor extends import_eventemitter3.default {
|
|
|
4413
4385
|
getShapesAtPoint(point, opts = {}) {
|
|
4414
4386
|
const margin = opts.margin ?? 0;
|
|
4415
4387
|
const candidateIds = this._spatialIndex.getShapeIdsAtPoint(point, margin);
|
|
4416
|
-
|
|
4417
|
-
|
|
4418
|
-
|
|
4419
|
-
|
|
4420
|
-
|
|
4388
|
+
const sorted = this.getCurrentPageShapesSorted();
|
|
4389
|
+
const result = [];
|
|
4390
|
+
for (let i = sorted.length - 1; i >= 0; i--) {
|
|
4391
|
+
const shape = sorted[i];
|
|
4392
|
+
if (this.isShapeHidden(shape)) continue;
|
|
4393
|
+
if (!candidateIds.has(shape.id) && !this.isShapeFrameLike(shape)) continue;
|
|
4394
|
+
if (this.isPointInShape(shape, point, opts)) result.push(shape);
|
|
4395
|
+
}
|
|
4396
|
+
return result;
|
|
4421
4397
|
}
|
|
4422
4398
|
/**
|
|
4423
4399
|
* Get shape IDs within the given bounds.
|
|
@@ -4502,9 +4478,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
4502
4478
|
const freshShape = this.getShape(id);
|
|
4503
4479
|
if (!freshShape) return new import_Vec.Vec(0, 0);
|
|
4504
4480
|
if ((0, import_tlschema.isPageId)(freshShape.parentId)) return import_Vec.Vec.From(point);
|
|
4505
|
-
|
|
4506
|
-
if (!parentTransform) return import_Vec.Vec.From(point);
|
|
4507
|
-
return parentTransform.clone().invert().applyToPoint(point);
|
|
4481
|
+
return this.getShapePageTransform(freshShape.parentId).clone().invert().applyToPoint(point);
|
|
4508
4482
|
}
|
|
4509
4483
|
getCurrentPageShapes() {
|
|
4510
4484
|
return Array.from(this.getCurrentPageShapeIds(), (id) => this.store.get(id));
|
|
@@ -4616,23 +4590,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
4616
4590
|
* @public
|
|
4617
4591
|
*/
|
|
4618
4592
|
isShapeInPage(shape, pageId = this.getCurrentPageId()) {
|
|
4619
|
-
|
|
4620
|
-
const shapeToCheck = this.getShape(id);
|
|
4621
|
-
if (!shapeToCheck) return false;
|
|
4622
|
-
let shapeIsInPage = false;
|
|
4623
|
-
if (shapeToCheck.parentId === pageId) {
|
|
4624
|
-
shapeIsInPage = true;
|
|
4625
|
-
} else {
|
|
4626
|
-
let parent = this.getShape(shapeToCheck.parentId);
|
|
4627
|
-
isInPageSearch: while (parent) {
|
|
4628
|
-
if (parent.parentId === pageId) {
|
|
4629
|
-
shapeIsInPage = true;
|
|
4630
|
-
break isInPageSearch;
|
|
4631
|
-
}
|
|
4632
|
-
parent = this.getShape(parent.parentId);
|
|
4633
|
-
}
|
|
4634
|
-
}
|
|
4635
|
-
return shapeIsInPage;
|
|
4593
|
+
return this.getAncestorPageId(shape) === pageId;
|
|
4636
4594
|
}
|
|
4637
4595
|
/**
|
|
4638
4596
|
* Get the id of the containing page for a given shape.
|
|
@@ -4713,10 +4671,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
4713
4671
|
for (let i = 0; i < shapesToReparent.length; i++) {
|
|
4714
4672
|
const shape = shapesToReparent[i];
|
|
4715
4673
|
const pageTransform = this.getShapePageTransform(shape);
|
|
4716
|
-
|
|
4717
|
-
const pagePoint = pageTransform.point();
|
|
4718
|
-
if (!pagePoint) continue;
|
|
4719
|
-
const newPoint = invertedParentTransform.applyToPoint(pagePoint);
|
|
4674
|
+
const newPoint = invertedParentTransform.applyToPoint(pageTransform.point());
|
|
4720
4675
|
const newRotation = pageTransform.rotation() - parentPageRotation;
|
|
4721
4676
|
if (shape.id === parentId) {
|
|
4722
4677
|
throw Error("Attempted to reparent a shape to itself!");
|
|
@@ -4805,7 +4760,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
4805
4760
|
*/
|
|
4806
4761
|
getShapeAndDescendantIds(ids) {
|
|
4807
4762
|
const shapeIds = /* @__PURE__ */ new Set();
|
|
4808
|
-
for (const shape of ids.map((id) => this.getShape(id)).sort(import_utils.sortByIndex)) {
|
|
4763
|
+
for (const shape of (0, import_utils.compact)(ids.map((id) => this.getShape(id))).sort(import_utils.sortByIndex)) {
|
|
4809
4764
|
shapeIds.add(shape.id);
|
|
4810
4765
|
this.visitDescendants(shape, (descendantId) => {
|
|
4811
4766
|
shapeIds.add(descendantId);
|
|
@@ -4827,11 +4782,12 @@ class Editor extends import_eventemitter3.default {
|
|
|
4827
4782
|
const draggingShapes = (0, import_utils.compact)(droppingShapes.map((s) => this.getShape(s))).filter(
|
|
4828
4783
|
(s) => !s.isLocked && !this.isShapeHidden(s)
|
|
4829
4784
|
);
|
|
4785
|
+
const excludedIds = this.getShapeAndDescendantIds(draggingShapes.map((s) => s.id));
|
|
4830
4786
|
const maybeDraggingOverShapes = this.getShapesAtPoint(point, {
|
|
4831
4787
|
hitInside: true,
|
|
4832
4788
|
margin: 0
|
|
4833
4789
|
}).filter(
|
|
4834
|
-
(s) => !droppingShapes.includes(s) && !s.isLocked && !this.isShapeHidden(s) && !
|
|
4790
|
+
(s) => !droppingShapes.includes(s) && !s.isLocked && !this.isShapeHidden(s) && !excludedIds.has(s.id)
|
|
4835
4791
|
);
|
|
4836
4792
|
for (const maybeDraggingOverShape of maybeDraggingOverShapes) {
|
|
4837
4793
|
const shapeUtil = this.getShapeUtil(maybeDraggingOverShape);
|
|
@@ -5084,8 +5040,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
5084
5040
|
for (const id of ids) {
|
|
5085
5041
|
const shape = this.getShape(id);
|
|
5086
5042
|
const localDelta = import_Vec.Vec.From(offset);
|
|
5087
|
-
|
|
5088
|
-
if (parentTransform) localDelta.rot(-parentTransform.rotation());
|
|
5043
|
+
localDelta.rot(-this.getShapeParentTransform(shape).rotation());
|
|
5089
5044
|
changes.push(this.getChangesToTranslateShape(shape, localDelta.add(shape)));
|
|
5090
5045
|
}
|
|
5091
5046
|
this.updateShapes(changes);
|
|
@@ -5140,7 +5095,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
5140
5095
|
if (!originalShape) continue;
|
|
5141
5096
|
let ox = 0;
|
|
5142
5097
|
let oy = 0;
|
|
5143
|
-
if (offset && initialIds.has(originalId)) {
|
|
5098
|
+
if (offset && initialIds.has(originalId) && !shapeIdSet.has(originalShape.parentId)) {
|
|
5144
5099
|
const parentTransform = this.getShapeParentTransform(originalShape);
|
|
5145
5100
|
const vec = new import_Vec.Vec(offset.x, offset.y).rot(-parentTransform.rotation());
|
|
5146
5101
|
ox = vec.x;
|
|
@@ -5254,26 +5209,17 @@ class Editor extends import_eventemitter3.default {
|
|
|
5254
5209
|
toggleLock(shapes) {
|
|
5255
5210
|
const ids = typeof shapes[0] === "string" ? shapes : shapes.map((s) => s.id);
|
|
5256
5211
|
if (this.getIsReadonly() || ids.length === 0) return this;
|
|
5257
|
-
let allLocked = true
|
|
5212
|
+
let allLocked = true;
|
|
5258
5213
|
const shapesToToggle = [];
|
|
5259
5214
|
for (const id of ids) {
|
|
5260
5215
|
const shape = this.getShape(id);
|
|
5261
5216
|
if (shape) {
|
|
5262
5217
|
shapesToToggle.push(shape);
|
|
5263
|
-
if (shape.isLocked)
|
|
5264
|
-
allUnlocked = false;
|
|
5265
|
-
} else {
|
|
5266
|
-
allLocked = false;
|
|
5267
|
-
}
|
|
5218
|
+
if (!shape.isLocked) allLocked = false;
|
|
5268
5219
|
}
|
|
5269
5220
|
}
|
|
5270
5221
|
this.run(() => {
|
|
5271
|
-
if (
|
|
5272
|
-
this.updateShapes(
|
|
5273
|
-
shapesToToggle.map((shape) => ({ id: shape.id, type: shape.type, isLocked: true }))
|
|
5274
|
-
);
|
|
5275
|
-
this.setSelectedShapes([]);
|
|
5276
|
-
} else if (allLocked) {
|
|
5222
|
+
if (allLocked) {
|
|
5277
5223
|
this.updateShapes(
|
|
5278
5224
|
shapesToToggle.map((shape) => ({ id: shape.id, type: shape.type, isLocked: false }))
|
|
5279
5225
|
);
|
|
@@ -5281,6 +5227,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
5281
5227
|
this.updateShapes(
|
|
5282
5228
|
shapesToToggle.map((shape) => ({ id: shape.id, type: shape.type, isLocked: true }))
|
|
5283
5229
|
);
|
|
5230
|
+
this.setSelectedShapes([]);
|
|
5284
5231
|
}
|
|
5285
5232
|
});
|
|
5286
5233
|
return this;
|
|
@@ -5391,9 +5338,10 @@ class Editor extends import_eventemitter3.default {
|
|
|
5391
5338
|
const ids = typeof shapes[0] === "string" ? shapes : shapes.map((s) => s.id);
|
|
5392
5339
|
let freshShapes = (0, import_utils.compact)(ids.map((id) => this.getShape(id)));
|
|
5393
5340
|
if (opts?.filterAxisAligned) {
|
|
5394
|
-
freshShapes = freshShapes.filter(
|
|
5395
|
-
|
|
5396
|
-
|
|
5341
|
+
freshShapes = freshShapes.filter((s) => {
|
|
5342
|
+
const remainder = Math.abs(this.getShapePageTransform(s).rotation() % import_utils2.HALF_PI);
|
|
5343
|
+
return Math.min(remainder, import_utils2.HALF_PI - remainder) < 1e-9;
|
|
5344
|
+
});
|
|
5397
5345
|
}
|
|
5398
5346
|
const clusters = [];
|
|
5399
5347
|
const allBounds = [];
|
|
@@ -5558,9 +5506,9 @@ class Editor extends import_eventemitter3.default {
|
|
|
5558
5506
|
dim = "height";
|
|
5559
5507
|
}
|
|
5560
5508
|
let shapeGap = 0;
|
|
5509
|
+
shapeClustersToStack.sort((a, b) => a.pageBounds[min] - b.pageBounds[min]);
|
|
5561
5510
|
if (_gap === 0) {
|
|
5562
5511
|
const gaps = {};
|
|
5563
|
-
shapeClustersToStack.sort((a, b) => a.pageBounds[min] - b.pageBounds[min]);
|
|
5564
5512
|
for (let i = 0; i < len - 1; i++) {
|
|
5565
5513
|
const currCluster = shapeClustersToStack[i];
|
|
5566
5514
|
const nextCluster = shapeClustersToStack[i + 1];
|
|
@@ -5598,8 +5546,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
5598
5546
|
const shapeDelta = delta.clone();
|
|
5599
5547
|
const parent = this.getShapeParent(shape);
|
|
5600
5548
|
if (parent) {
|
|
5601
|
-
|
|
5602
|
-
if (parentTransform) shapeDelta.rot(-parentTransform.rotation());
|
|
5549
|
+
shapeDelta.rot(-this.getShapePageTransform(parent).rotation());
|
|
5603
5550
|
}
|
|
5604
5551
|
shapeDelta.add(shape);
|
|
5605
5552
|
changes.push(this.getChangesToTranslateShape(shape, shapeDelta));
|
|
@@ -5637,7 +5584,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
5637
5584
|
}
|
|
5638
5585
|
const commonBounds = import_Box.Box.Common(allBounds);
|
|
5639
5586
|
const maxWidth = commonBounds.width;
|
|
5640
|
-
shapeClustersToPack.sort((a, b) =>
|
|
5587
|
+
shapeClustersToPack.sort((a, b) => b.pageBounds.width - a.pageBounds.width).sort((a, b) => b.pageBounds.height - a.pageBounds.height);
|
|
5641
5588
|
const startWidth = Math.max(Math.ceil(Math.sqrt(area / 0.95)), maxWidth);
|
|
5642
5589
|
const spaces = [new import_Box.Box(commonBounds.x, commonBounds.y, startWidth, Infinity)];
|
|
5643
5590
|
let width = 0;
|
|
@@ -5685,8 +5632,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
5685
5632
|
const shapeDelta = delta.clone();
|
|
5686
5633
|
const parent = this.getShapeParent(shape);
|
|
5687
5634
|
if (parent) {
|
|
5688
|
-
|
|
5689
|
-
if (parentTransform) shapeDelta.rot(-parentTransform.rotation());
|
|
5635
|
+
shapeDelta.rot(-this.getShapeParentTransform(shape).rotation());
|
|
5690
5636
|
}
|
|
5691
5637
|
shapeDelta.add(shape);
|
|
5692
5638
|
changes.push(this.getChangesToTranslateShape(shape, shapeDelta));
|
|
@@ -5752,8 +5698,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
5752
5698
|
const shapeDelta = delta.clone();
|
|
5753
5699
|
const parent = this.getShapeParent(shape);
|
|
5754
5700
|
if (parent) {
|
|
5755
|
-
|
|
5756
|
-
if (parentTransform) shapeDelta.rot(-parentTransform.rotation());
|
|
5701
|
+
shapeDelta.rot(-this.getShapePageTransform(parent).rotation());
|
|
5757
5702
|
}
|
|
5758
5703
|
shapeDelta.add(shape);
|
|
5759
5704
|
changes.push(this.getChangesToTranslateShape(shape, shapeDelta));
|
|
@@ -5827,8 +5772,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
5827
5772
|
const shapeDelta = delta.clone();
|
|
5828
5773
|
const parent = this.getShapeParent(shape);
|
|
5829
5774
|
if (parent) {
|
|
5830
|
-
|
|
5831
|
-
if (parentTransform) shapeDelta.rot(-parentTransform.rotation());
|
|
5775
|
+
shapeDelta.rot(-this.getShapePageTransform(parent).rotation());
|
|
5832
5776
|
}
|
|
5833
5777
|
shapeDelta.add(shape);
|
|
5834
5778
|
changes.push(this.getChangesToTranslateShape(shape, shapeDelta));
|
|
@@ -5883,8 +5827,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
5883
5827
|
scale[val] = commonBounds[dim] / pageBounds[dim];
|
|
5884
5828
|
for (const shape of shapes2) {
|
|
5885
5829
|
const shapeLocalOffset = localOffset.clone();
|
|
5886
|
-
|
|
5887
|
-
if (parentTransform) shapeLocalOffset.rot(-parentTransform.rotation());
|
|
5830
|
+
shapeLocalOffset.rot(-this.getShapeParentTransform(shape).rotation());
|
|
5888
5831
|
shapeLocalOffset.add(shape);
|
|
5889
5832
|
const changes = this.getChangesToTranslateShape(shape, shapeLocalOffset);
|
|
5890
5833
|
this.updateShape(changes);
|
|
@@ -5940,8 +5883,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
5940
5883
|
);
|
|
5941
5884
|
for (const shape of shapes2) {
|
|
5942
5885
|
const shapeLocalOffset = localOffset.clone();
|
|
5943
|
-
|
|
5944
|
-
if (parentTransform) shapeLocalOffset.rot(-parentTransform.rotation());
|
|
5886
|
+
shapeLocalOffset.rot(-this.getShapeParentTransform(shape).rotation());
|
|
5945
5887
|
shapeLocalOffset.add(shape);
|
|
5946
5888
|
const changes = this.getChangesToTranslateShape(shape, shapeLocalOffset);
|
|
5947
5889
|
this.updateShape(changes);
|
|
@@ -5990,9 +5932,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
5990
5932
|
const scaleOrigin = opts.scaleOrigin ?? this.getShapePageBounds(id)?.center;
|
|
5991
5933
|
if (!scaleOrigin) return null;
|
|
5992
5934
|
const pageTransform = opts.initialPageTransform ? import_Mat.Mat.Cast(opts.initialPageTransform) : this.getShapePageTransform(id);
|
|
5993
|
-
if (!pageTransform) return null;
|
|
5994
5935
|
const pageRotation = pageTransform.rotation();
|
|
5995
|
-
if (pageRotation == null) return null;
|
|
5996
5936
|
const scaleAxisRotation = opts.scaleAxisRotation ?? pageRotation;
|
|
5997
5937
|
const initialBounds = opts.initialBounds ?? this.getShapeGeometry(id).bounds;
|
|
5998
5938
|
if (!initialBounds) return null;
|
|
@@ -6143,7 +6083,6 @@ class Editor extends import_eventemitter3.default {
|
|
|
6143
6083
|
const currentLocalBounds = this.getShapeGeometry(id).bounds;
|
|
6144
6084
|
const currentPageCenter = import_Mat.Mat.applyToPoint(pageTransform, currentLocalBounds.center);
|
|
6145
6085
|
const shapePageTransformOrigin = pageTransform.point();
|
|
6146
|
-
if (!currentPageCenter || !shapePageTransformOrigin) return this;
|
|
6147
6086
|
const pageDelta = import_Vec.Vec.Sub(postScaleShapePageCenter, currentPageCenter);
|
|
6148
6087
|
const postScaleShapePagePoint = import_Vec.Vec.Add(shapePageTransformOrigin, pageDelta);
|
|
6149
6088
|
const { x, y } = this.getPointInParentSpace(id, postScaleShapePagePoint);
|
|
@@ -6402,10 +6341,10 @@ class Editor extends import_eventemitter3.default {
|
|
|
6402
6341
|
if (animationIdForShape !== animationId) continue;
|
|
6403
6342
|
updates.push({
|
|
6404
6343
|
...end,
|
|
6405
|
-
x: start.x
|
|
6406
|
-
y: start.y
|
|
6407
|
-
opacity: start.opacity
|
|
6408
|
-
rotation: start.rotation
|
|
6344
|
+
x: (0, import_utils.lerp)(start.x, end.x, t),
|
|
6345
|
+
y: (0, import_utils.lerp)(start.y, end.y, t),
|
|
6346
|
+
opacity: (0, import_utils.lerp)(start.opacity, end.opacity, t),
|
|
6347
|
+
rotation: (0, import_utils.lerp)(start.rotation, end.rotation, t),
|
|
6409
6348
|
props: this.getShapeUtil(end).getInterpolatedProps?.(start, end, t) ?? end.props
|
|
6410
6349
|
});
|
|
6411
6350
|
}
|
|
@@ -6531,7 +6470,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
6531
6470
|
* @public
|
|
6532
6471
|
*/
|
|
6533
6472
|
updateShapes(partials) {
|
|
6534
|
-
const compactedPartials =
|
|
6473
|
+
const compactedPartials = [];
|
|
6535
6474
|
for (let i = 0, n = partials.length; i < n; i++) {
|
|
6536
6475
|
const partial = partials[i];
|
|
6537
6476
|
if (!partial) continue;
|
|
@@ -6602,28 +6541,32 @@ class Editor extends import_eventemitter3.default {
|
|
|
6602
6541
|
}
|
|
6603
6542
|
/* --------------------- Styles --------------------- */
|
|
6604
6543
|
/**
|
|
6605
|
-
*
|
|
6544
|
+
* Groups have no styles of their own: a style read or write on a selection applies to the
|
|
6545
|
+
* non-group shapes beneath each group, however deeply nested. Returns those shapes.
|
|
6606
6546
|
*
|
|
6607
6547
|
* @internal
|
|
6608
6548
|
*/
|
|
6609
|
-
|
|
6610
|
-
|
|
6611
|
-
|
|
6612
|
-
if (
|
|
6613
|
-
|
|
6614
|
-
|
|
6615
|
-
|
|
6616
|
-
|
|
6617
|
-
|
|
6618
|
-
|
|
6549
|
+
_getStyleableShapes(shapes) {
|
|
6550
|
+
const result = [];
|
|
6551
|
+
const visit = (shape) => {
|
|
6552
|
+
if (this.isShapeOfType(shape, "group")) {
|
|
6553
|
+
for (const childId of this.getSortedChildIdsForParent(shape.id)) {
|
|
6554
|
+
const child = this.getShape(childId);
|
|
6555
|
+
if (child) visit(child);
|
|
6556
|
+
}
|
|
6557
|
+
} else {
|
|
6558
|
+
result.push(shape);
|
|
6619
6559
|
}
|
|
6620
|
-
}
|
|
6560
|
+
};
|
|
6561
|
+
for (const shape of shapes) visit(shape);
|
|
6562
|
+
return result;
|
|
6621
6563
|
}
|
|
6622
6564
|
_getSelectionSharedStyles() {
|
|
6623
|
-
const selectedShapes = this.getSelectedShapes();
|
|
6624
6565
|
const sharedStyles = new import_SharedStylesMap.SharedStyleMap();
|
|
6625
|
-
for (const
|
|
6626
|
-
|
|
6566
|
+
for (const shape of this._getStyleableShapes(this.getSelectedShapes())) {
|
|
6567
|
+
for (const [style, propKey] of this.styleProps[shape.type]) {
|
|
6568
|
+
sharedStyles.applyValue(style, (0, import_utils.getOwnProperty)(shape.props, propKey));
|
|
6569
|
+
}
|
|
6627
6570
|
}
|
|
6628
6571
|
return sharedStyles;
|
|
6629
6572
|
}
|
|
@@ -6655,38 +6598,16 @@ class Editor extends import_eventemitter3.default {
|
|
|
6655
6598
|
const styles = new import_SharedStylesMap.SharedStyleMap();
|
|
6656
6599
|
if (!currentTool) return styles;
|
|
6657
6600
|
if (currentTool.shapeType) {
|
|
6658
|
-
|
|
6659
|
-
|
|
6660
|
-
if (style.id === "tldraw:color") continue;
|
|
6661
|
-
styles.applyValue(style, this.getStyleForNextShape(style));
|
|
6662
|
-
}
|
|
6663
|
-
} else {
|
|
6664
|
-
for (const style of this.styleProps[currentTool.shapeType].keys()) {
|
|
6665
|
-
styles.applyValue(style, this.getStyleForNextShape(style));
|
|
6666
|
-
}
|
|
6601
|
+
for (const style of this.styleProps[currentTool.shapeType].keys()) {
|
|
6602
|
+
styles.applyValue(style, this.getStyleForNextShape(style));
|
|
6667
6603
|
}
|
|
6668
6604
|
}
|
|
6669
6605
|
return styles;
|
|
6670
6606
|
}
|
|
6671
6607
|
getSharedOpacity() {
|
|
6672
6608
|
if (this.isIn("select") && this.getSelectedShapeIds().length > 0) {
|
|
6673
|
-
const shapesToCheck = [];
|
|
6674
|
-
const addShape = (shapeId) => {
|
|
6675
|
-
const shape = this.getShape(shapeId);
|
|
6676
|
-
if (!shape) return;
|
|
6677
|
-
if (this.isShapeOfType(shape, "group")) {
|
|
6678
|
-
for (const childId of this.getSortedChildIdsForParent(shape.id)) {
|
|
6679
|
-
addShape(childId);
|
|
6680
|
-
}
|
|
6681
|
-
} else {
|
|
6682
|
-
shapesToCheck.push(shape);
|
|
6683
|
-
}
|
|
6684
|
-
};
|
|
6685
|
-
for (const shapeId of this.getSelectedShapeIds()) {
|
|
6686
|
-
addShape(shapeId);
|
|
6687
|
-
}
|
|
6688
6609
|
let opacity = null;
|
|
6689
|
-
for (const shape of
|
|
6610
|
+
for (const shape of this._getStyleableShapes(this.getSelectedShapes())) {
|
|
6690
6611
|
if (opacity === null) {
|
|
6691
6612
|
opacity = shape.opacity;
|
|
6692
6613
|
} else if (opacity !== shape.opacity) {
|
|
@@ -6725,28 +6646,12 @@ class Editor extends import_eventemitter3.default {
|
|
|
6725
6646
|
setOpacityForSelectedShapes(opacity) {
|
|
6726
6647
|
const selectedShapes = this.getSelectedShapes();
|
|
6727
6648
|
if (selectedShapes.length > 0) {
|
|
6728
|
-
const shapesToUpdate = [];
|
|
6729
|
-
const addShapeById = (shape) => {
|
|
6730
|
-
if (this.isShapeOfType(shape, "group")) {
|
|
6731
|
-
const childIds = this.getSortedChildIdsForParent(shape);
|
|
6732
|
-
for (const childId of childIds) {
|
|
6733
|
-
addShapeById(this.getShape(childId));
|
|
6734
|
-
}
|
|
6735
|
-
} else {
|
|
6736
|
-
shapesToUpdate.push(shape);
|
|
6737
|
-
}
|
|
6738
|
-
};
|
|
6739
|
-
for (const id of selectedShapes) {
|
|
6740
|
-
addShapeById(id);
|
|
6741
|
-
}
|
|
6742
6649
|
this.updateShapes(
|
|
6743
|
-
|
|
6744
|
-
|
|
6745
|
-
|
|
6746
|
-
|
|
6747
|
-
|
|
6748
|
-
};
|
|
6749
|
-
})
|
|
6650
|
+
this._getStyleableShapes(selectedShapes).map((shape) => ({
|
|
6651
|
+
id: shape.id,
|
|
6652
|
+
type: shape.type,
|
|
6653
|
+
opacity
|
|
6654
|
+
}))
|
|
6750
6655
|
);
|
|
6751
6656
|
}
|
|
6752
6657
|
return this;
|
|
@@ -6791,33 +6696,17 @@ class Editor extends import_eventemitter3.default {
|
|
|
6791
6696
|
const selectedShapes = this.getSelectedShapes();
|
|
6792
6697
|
if (selectedShapes.length > 0) {
|
|
6793
6698
|
const updates = [];
|
|
6794
|
-
const
|
|
6795
|
-
|
|
6796
|
-
|
|
6797
|
-
|
|
6798
|
-
|
|
6799
|
-
|
|
6800
|
-
|
|
6801
|
-
|
|
6802
|
-
const stylePropKey = this.styleProps[shape.type].get(style);
|
|
6803
|
-
if (stylePropKey) {
|
|
6804
|
-
const shapePartial = {
|
|
6805
|
-
id: shape.id,
|
|
6806
|
-
type: shape.type,
|
|
6807
|
-
props: { [stylePropKey]: value }
|
|
6808
|
-
};
|
|
6809
|
-
updates.push({
|
|
6810
|
-
util,
|
|
6811
|
-
originalShape: shape,
|
|
6812
|
-
updatePartial: shapePartial
|
|
6813
|
-
});
|
|
6814
|
-
}
|
|
6699
|
+
for (const shape of this._getStyleableShapes(selectedShapes)) {
|
|
6700
|
+
const stylePropKey = this.styleProps[shape.type].get(style);
|
|
6701
|
+
if (stylePropKey) {
|
|
6702
|
+
updates.push({
|
|
6703
|
+
id: shape.id,
|
|
6704
|
+
type: shape.type,
|
|
6705
|
+
props: { [stylePropKey]: value }
|
|
6706
|
+
});
|
|
6815
6707
|
}
|
|
6816
|
-
};
|
|
6817
|
-
for (const shape of selectedShapes) {
|
|
6818
|
-
addShapeById(shape);
|
|
6819
6708
|
}
|
|
6820
|
-
this.updateShapes(updates
|
|
6709
|
+
this.updateShapes(updates);
|
|
6821
6710
|
}
|
|
6822
6711
|
return this;
|
|
6823
6712
|
}
|
|
@@ -7213,7 +7102,6 @@ class Editor extends import_eventemitter3.default {
|
|
|
7213
7102
|
if (shapeIdMap.has(newShape.parentId)) {
|
|
7214
7103
|
newShape.parentId = shapeIdMap.get(oldShape.parentId);
|
|
7215
7104
|
} else {
|
|
7216
|
-
rootShapeIds.push(newShape.id);
|
|
7217
7105
|
newShape.index = index;
|
|
7218
7106
|
index = (0, import_utils.getIndexAbove)(index);
|
|
7219
7107
|
}
|
|
@@ -7238,8 +7126,11 @@ class Editor extends import_eventemitter3.default {
|
|
|
7238
7126
|
continue;
|
|
7239
7127
|
}
|
|
7240
7128
|
if (asset.type === "image" && asset.props.src?.startsWith("data:image") || asset.type === "video" && asset.props.src?.startsWith("data:video")) {
|
|
7241
|
-
assetsToUpdate.push(
|
|
7242
|
-
|
|
7129
|
+
assetsToUpdate.push(asset);
|
|
7130
|
+
const assetWithoutSrc = (0, import_utils.structuredClone)(asset);
|
|
7131
|
+
assetWithoutSrc.props.src = null;
|
|
7132
|
+
assetsToCreate.push(assetWithoutSrc);
|
|
7133
|
+
continue;
|
|
7243
7134
|
}
|
|
7244
7135
|
assetsToCreate.push(asset);
|
|
7245
7136
|
}
|
|
@@ -8066,7 +7957,7 @@ class Editor extends import_eventemitter3.default {
|
|
|
8066
7957
|
if (info.type === "misc") {
|
|
8067
7958
|
if (info.name === "cancel" || info.name === "complete") {
|
|
8068
7959
|
this.inputs.setIsDragging(false);
|
|
8069
|
-
if (this.inputs.getIsPanning()) {
|
|
7960
|
+
if (this.inputs.getIsPanning() && !this.inputs.keys.has("Space")) {
|
|
8070
7961
|
this.inputs.setIsPanning(false);
|
|
8071
7962
|
this.inputs.setIsSpacebarPanning(false);
|
|
8072
7963
|
this.setCursor({ type: this._prevCursor, rotation: 0 });
|
|
@@ -8818,10 +8709,9 @@ function withIsolatedShapes(editor, shapeIds, callback) {
|
|
|
8818
8709
|
}
|
|
8819
8710
|
function getCameraFitXFitY(editor, cameraOptions) {
|
|
8820
8711
|
if (!cameraOptions.constraints) throw Error("Should have constraints here");
|
|
8821
|
-
const {
|
|
8822
|
-
padding: { x: px, y: py }
|
|
8823
|
-
} = cameraOptions.constraints;
|
|
8824
8712
|
const vsb = editor.getViewportScreenBounds();
|
|
8713
|
+
const px = Math.min(cameraOptions.constraints.padding.x, vsb.w / 2);
|
|
8714
|
+
const py = Math.min(cameraOptions.constraints.padding.y, vsb.h / 2);
|
|
8825
8715
|
const bounds = import_Box.Box.From(cameraOptions.constraints.bounds);
|
|
8826
8716
|
const zx = (vsb.w - px * 2) / bounds.w;
|
|
8827
8717
|
const zy = (vsb.h - py * 2) / bounds.h;
|