@formicoidea/labre-core 0.43.1 → 0.45.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/_pkgs/affine-block-attachment/utils.js +4 -0
- package/dist/_pkgs/affine-block-bookmark/configs/toolbar.js +17 -4
- package/dist/_pkgs/affine-block-callout/commands/turn-into-callout.d.ts +29 -0
- package/dist/_pkgs/affine-block-callout/commands/turn-into-callout.js +81 -0
- package/dist/_pkgs/affine-block-callout/configs/slash-menu.js +6 -4
- package/dist/_pkgs/affine-block-callout/configs/turn-into.d.ts +8 -0
- package/dist/_pkgs/affine-block-callout/configs/turn-into.js +19 -0
- package/dist/_pkgs/affine-block-callout/translations.d.ts +4 -2
- package/dist/_pkgs/affine-block-callout/translations.js +4 -2
- package/dist/_pkgs/affine-block-callout/view.js +3 -0
- package/dist/_pkgs/affine-block-code/code-block-service.d.ts +13 -0
- package/dist/_pkgs/affine-block-code/code-block-service.js +26 -0
- package/dist/_pkgs/affine-block-code/code-block.d.ts +6 -0
- package/dist/_pkgs/affine-block-code/code-block.js +11 -2
- package/dist/_pkgs/affine-block-code/code-toolbar/components/lang-button.js +31 -8
- package/dist/_pkgs/affine-block-edgeless-text/edgeless-toolbar/config.d.ts +11 -0
- package/dist/_pkgs/affine-block-edgeless-text/svg-painter.d.ts +20 -0
- package/dist/_pkgs/affine-block-edgeless-text/svg-painter.js +76 -0
- package/dist/_pkgs/affine-block-edgeless-text/view.js +2 -0
- package/dist/_pkgs/affine-block-embed/configs/toolbar.js +11 -2
- package/dist/_pkgs/affine-block-embed/embed-iframe-block/configs/toolbar.js +11 -2
- package/dist/_pkgs/affine-block-embed-doc/embed-linked-doc-block/embed-edgeless-linked-doc-block.js +3 -1
- package/dist/_pkgs/affine-block-embed-doc/embed-synced-doc-block/configs/toolbar.js +7 -2
- package/dist/_pkgs/affine-block-embed-doc/embed-synced-doc-block/embed-edgeless-synced-doc-block.js +3 -1
- package/dist/_pkgs/affine-block-frame/frame-manager.d.ts +5 -0
- package/dist/_pkgs/affine-block-frame/frame-manager.js +48 -17
- package/dist/_pkgs/affine-block-frame/frame-tool.js +3 -1
- package/dist/_pkgs/affine-block-image/utils.js +4 -1
- package/dist/_pkgs/affine-block-latex/adapters/markdown/preprocessor.d.ts +8 -0
- package/dist/_pkgs/affine-block-latex/adapters/markdown/preprocessor.js +9 -5
- package/dist/_pkgs/affine-block-note/translations.d.ts +0 -1
- package/dist/_pkgs/affine-block-note/translations.js +0 -5
- package/dist/_pkgs/affine-block-root/configs/toolbar.js +17 -1
- package/dist/_pkgs/affine-block-root/edgeless/clipboard/clipboard.js +2 -1
- package/dist/_pkgs/affine-block-root/edgeless/clipboard/command.js +161 -83
- package/dist/_pkgs/affine-block-root/edgeless/clipboard/paste-order.d.ts +21 -0
- package/dist/_pkgs/affine-block-root/edgeless/clipboard/paste-order.js +85 -0
- package/dist/_pkgs/affine-block-root/edgeless/edgeless-root-block.d.ts +6 -0
- package/dist/_pkgs/affine-block-root/edgeless/edgeless-root-block.js +18 -1
- package/dist/_pkgs/affine-block-root/edgeless/utils/clone-utils.d.ts +9 -0
- package/dist/_pkgs/affine-block-root/edgeless/utils/clone-utils.js +28 -0
- package/dist/_pkgs/affine-block-root/keyboard/commands.js +9 -6
- package/dist/_pkgs/affine-block-root/preview/edgeless-root-preview-block.js +15 -2
- package/dist/_pkgs/affine-block-surface/adapters/markdown/element-adapter/type.d.ts +1 -1
- package/dist/_pkgs/affine-block-surface/element-model/index.d.ts +1 -1
- package/dist/_pkgs/affine-block-surface/element-model/index.js +1 -1
- package/dist/_pkgs/affine-block-surface/extensions/audit.js +13 -61
- package/dist/_pkgs/affine-block-surface/extensions/canvas-grid/commands.d.ts +2 -0
- package/dist/_pkgs/affine-block-surface/extensions/canvas-grid/commands.js +71 -0
- package/dist/_pkgs/affine-block-surface/extensions/canvas-grid/index.d.ts +1 -0
- package/dist/_pkgs/affine-block-surface/extensions/canvas-grid/index.js +1 -0
- package/dist/_pkgs/affine-block-surface/extensions/clipboard-config.js +4 -0
- package/dist/_pkgs/affine-block-surface/extensions/crud-extension.js +4 -0
- package/dist/_pkgs/affine-block-surface/extensions/export-manager/export-manager.d.ts +12 -0
- package/dist/_pkgs/affine-block-surface/extensions/export-manager/export-manager.js +27 -7
- package/dist/_pkgs/affine-block-surface/extensions/export-svg/command.d.ts +2 -1
- package/dist/_pkgs/affine-block-surface/extensions/export-svg/command.js +22 -3
- package/dist/_pkgs/affine-block-surface/extensions/export-svg/index.d.ts +6 -3
- package/dist/_pkgs/affine-block-surface/extensions/export-svg/index.js +4 -2
- package/dist/_pkgs/affine-block-surface/extensions/export-svg/parts.d.ts +63 -0
- package/dist/_pkgs/affine-block-surface/extensions/export-svg/parts.js +67 -0
- package/dist/_pkgs/affine-block-surface/extensions/export-svg/render.d.ts +62 -5
- package/dist/_pkgs/affine-block-surface/extensions/export-svg/render.js +98 -18
- package/dist/_pkgs/affine-block-surface/extensions/export-svg/svg-context.d.ts +14 -0
- package/dist/_pkgs/affine-block-surface/extensions/export-svg/svg-context.js +82 -1
- package/dist/_pkgs/affine-block-surface/extensions/export-svg/toolbar.d.ts +2 -2
- package/dist/_pkgs/affine-block-surface/extensions/export-svg/toolbar.js +112 -10
- package/dist/_pkgs/affine-block-surface/extensions/export-svg/translations.d.ts +13 -0
- package/dist/_pkgs/affine-block-surface/extensions/export-svg/translations.js +33 -0
- package/dist/_pkgs/affine-block-surface/extensions/index.d.ts +3 -0
- package/dist/_pkgs/affine-block-surface/extensions/index.js +3 -0
- package/dist/_pkgs/affine-block-surface/extensions/reading-widget.d.ts +13 -6
- package/dist/_pkgs/affine-block-surface/extensions/reading-widget.js +26 -10
- package/dist/_pkgs/affine-block-surface/extensions/reading.d.ts +82 -6
- package/dist/_pkgs/affine-block-surface/extensions/reading.js +99 -21
- package/dist/_pkgs/affine-block-surface/extensions/selection-pane/actions.d.ts +80 -0
- package/dist/_pkgs/affine-block-surface/extensions/selection-pane/actions.js +248 -0
- package/dist/_pkgs/affine-block-surface/extensions/selection-pane/commands.d.ts +82 -0
- package/dist/_pkgs/affine-block-surface/extensions/selection-pane/commands.js +342 -0
- package/dist/_pkgs/affine-block-surface/extensions/selection-pane/index.d.ts +3 -0
- package/dist/_pkgs/affine-block-surface/extensions/selection-pane/index.js +3 -0
- package/dist/_pkgs/affine-block-surface/extensions/selection-pane/tree.d.ts +137 -0
- package/dist/_pkgs/affine-block-surface/extensions/selection-pane/tree.js +323 -0
- package/dist/_pkgs/affine-block-surface/extensions/svg-sketch.d.ts +112 -4
- package/dist/_pkgs/affine-block-surface/extensions/svg-sketch.js +86 -15
- package/dist/_pkgs/affine-block-surface/extensions/user-layers/actions.d.ts +76 -0
- package/dist/_pkgs/affine-block-surface/extensions/user-layers/actions.js +299 -0
- package/dist/_pkgs/affine-block-surface/extensions/user-layers/active-layer.d.ts +20 -0
- package/dist/_pkgs/affine-block-surface/extensions/user-layers/active-layer.js +34 -0
- package/dist/_pkgs/affine-block-surface/extensions/user-layers/commands.d.ts +67 -0
- package/dist/_pkgs/affine-block-surface/extensions/user-layers/commands.js +172 -0
- package/dist/_pkgs/affine-block-surface/extensions/user-layers/creation.d.ts +40 -0
- package/dist/_pkgs/affine-block-surface/extensions/user-layers/creation.js +69 -0
- package/dist/_pkgs/affine-block-surface/extensions/user-layers/index.d.ts +5 -0
- package/dist/_pkgs/affine-block-surface/extensions/user-layers/index.js +5 -0
- package/dist/_pkgs/affine-block-surface/extensions/user-layers/translations.d.ts +10 -0
- package/dist/_pkgs/affine-block-surface/extensions/user-layers/translations.js +14 -0
- package/dist/_pkgs/affine-block-surface/framework-background/facts.d.ts +55 -2
- package/dist/_pkgs/affine-block-surface/framework-background/facts.js +63 -1
- package/dist/_pkgs/affine-block-surface/framework-background/stacking.d.ts +16 -8
- package/dist/_pkgs/affine-block-surface/framework-background/stacking.js +26 -14
- package/dist/_pkgs/affine-block-surface/renderer/canvas-renderer.js +17 -3
- package/dist/_pkgs/affine-block-surface/renderer/dom-renderer.d.ts +3 -1
- package/dist/_pkgs/affine-block-surface/renderer/dom-renderer.js +22 -2
- package/dist/_pkgs/affine-block-surface/renderer/paint-predicate.d.ts +30 -0
- package/dist/_pkgs/affine-block-surface/renderer/paint-predicate.js +29 -0
- package/dist/_pkgs/affine-block-surface/surface-block.js +6 -0
- package/dist/_pkgs/affine-block-surface/surface-model.js +5 -0
- package/dist/_pkgs/affine-block-surface/surface-transformer.js +5 -0
- package/dist/_pkgs/affine-block-surface/tool/default-tool.js +28 -5
- package/dist/_pkgs/affine-block-surface/view.js +23 -1
- package/dist/_pkgs/affine-block-surface-ref/surface-ref-block.js +12 -2
- package/dist/_pkgs/affine-components/context-menu/button.js +14 -0
- package/dist/_pkgs/affine-components/filterable-list/index.js +30 -9
- package/dist/_pkgs/affine-components/icons/index.d.ts +0 -1
- package/dist/_pkgs/affine-components/icons/index.js +0 -1
- package/dist/_pkgs/affine-components/icons/text.d.ts +1 -0
- package/dist/_pkgs/affine-components/icons/text.js +11 -0
- package/dist/_pkgs/affine-fragment-adapter-panel/adapter-panel.d.ts +2 -2
- package/dist/_pkgs/affine-fragment-frame-panel/card/frame-card.js +2 -2
- package/dist/_pkgs/affine-fragment-frame-panel/header/frame-panel-header.d.ts +1 -1
- package/dist/_pkgs/affine-fragment-frame-panel/header/frame-panel-header.js +8 -27
- package/dist/_pkgs/affine-fragment-frame-panel/index.d.ts +1 -0
- package/dist/_pkgs/affine-fragment-frame-panel/index.js +1 -0
- package/dist/_pkgs/affine-gfx-connector/element-renderer/connector-dom/index.js +3 -1
- package/dist/_pkgs/affine-gfx-connector/element-renderer/index.js +21 -4
- package/dist/_pkgs/affine-gfx-connector/text/edgeless-connector-label-editor.js +3 -2
- package/dist/_pkgs/affine-gfx-connector/toolbar/config.js +1 -1
- package/dist/_pkgs/affine-gfx-group/command/group-api.js +52 -1
- package/dist/_pkgs/affine-gfx-shape/element-renderer/shape/index.js +21 -3
- package/dist/_pkgs/affine-gfx-shape/text/edgeless-shape-text-editor.js +2 -0
- package/dist/_pkgs/affine-gfx-shape/toolbar/config.js +1 -1
- package/dist/_pkgs/affine-gfx-template/services/template-middlewares.d.ts +9 -0
- package/dist/_pkgs/affine-gfx-template/services/template-middlewares.js +23 -1
- package/dist/_pkgs/affine-gfx-template/services/template.js +2 -1
- package/dist/_pkgs/affine-gfx-text/edgeless-text-editor.js +2 -1
- package/dist/_pkgs/affine-gfx-text/element-renderer/index.js +20 -3
- package/dist/_pkgs/affine-gfx-text/element-renderer/utils.d.ts +67 -1
- package/dist/_pkgs/affine-gfx-text/element-renderer/utils.js +101 -0
- package/dist/_pkgs/affine-gfx-text/toolbar/actions.d.ts +11 -0
- package/dist/_pkgs/affine-gfx-text/toolbar/actions.js +53 -2
- package/dist/_pkgs/affine-gfx-text/toolbar/config.d.ts +11 -0
- package/dist/_pkgs/affine-gfx-text/toolbar/config.js +1 -1
- package/dist/_pkgs/affine-inline-preset/adapters/html/html-inline.d.ts +3 -0
- package/dist/_pkgs/affine-inline-preset/adapters/html/html-inline.js +31 -0
- package/dist/_pkgs/affine-inline-preset/adapters/html/inline-delta.d.ts +4 -0
- package/dist/_pkgs/affine-inline-preset/adapters/html/inline-delta.js +14 -0
- package/dist/_pkgs/affine-inline-preset/command/config.js +21 -3
- package/dist/_pkgs/affine-inline-preset/command/index.d.ts +1 -1
- package/dist/_pkgs/affine-inline-preset/command/index.js +1 -1
- package/dist/_pkgs/affine-inline-preset/command/text-style.d.ts +2 -1
- package/dist/_pkgs/affine-inline-preset/command/text-style.js +1 -0
- package/dist/_pkgs/affine-inline-preset/default-inline-manager.js +2 -1
- package/dist/_pkgs/affine-inline-preset/inline-spec.d.ts +4 -0
- package/dist/_pkgs/affine-inline-preset/inline-spec.js +14 -0
- package/dist/_pkgs/affine-inline-preset/translations.d.ts +2 -2
- package/dist/_pkgs/affine-inline-preset/translations.js +2 -2
- package/dist/_pkgs/affine-model/blocks/attachment/attachment-model.js +2 -0
- package/dist/_pkgs/affine-model/blocks/bookmark/bookmark-model.js +2 -0
- package/dist/_pkgs/affine-model/blocks/edgeless-text/edgeless-text-model.d.ts +1 -1
- package/dist/_pkgs/affine-model/blocks/edgeless-text/edgeless-text-model.js +2 -0
- package/dist/_pkgs/affine-model/blocks/embed/iframe/iframe-model.js +2 -0
- package/dist/_pkgs/affine-model/blocks/frame/frame-model.js +2 -0
- package/dist/_pkgs/affine-model/blocks/image/image-model.js +2 -0
- package/dist/_pkgs/affine-model/blocks/latex/latex-model.js +2 -0
- package/dist/_pkgs/affine-model/blocks/note/note-model.js +2 -0
- package/dist/_pkgs/affine-model/consts/text.d.ts +26 -0
- package/dist/_pkgs/affine-model/consts/text.js +25 -0
- package/dist/_pkgs/affine-model/elements/shape/shape.d.ts +6 -1
- package/dist/_pkgs/affine-model/elements/shape/shape.js +14 -1
- package/dist/_pkgs/affine-model/elements/text/text.d.ts +6 -1
- package/dist/_pkgs/affine-model/elements/text/text.js +13 -1
- package/dist/_pkgs/affine-model/utils/helper.js +2 -0
- package/dist/_pkgs/affine-rich-text/conversion.d.ts +25 -0
- package/dist/_pkgs/affine-rich-text/conversion.js +9 -0
- package/dist/_pkgs/affine-rich-text/index.d.ts +1 -1
- package/dist/_pkgs/affine-rich-text/index.js +1 -1
- package/dist/_pkgs/affine-shared/commands/model-crud/replace-selected-text-with-blocks.d.ts +1 -1
- package/dist/_pkgs/affine-shared/services/canvas-grid.d.ts +63 -0
- package/dist/_pkgs/affine-shared/services/canvas-grid.js +109 -0
- package/dist/_pkgs/affine-shared/services/canvas-local-visibility.d.ts +64 -0
- package/dist/_pkgs/affine-shared/services/canvas-local-visibility.js +192 -0
- package/dist/_pkgs/affine-shared/services/edit-props-store.d.ts +27 -0
- package/dist/_pkgs/affine-shared/services/edit-props-store.js +34 -0
- package/dist/_pkgs/affine-shared/services/editor-setting-service.d.ts +3 -0
- package/dist/_pkgs/affine-shared/services/editor-setting-service.js +7 -0
- package/dist/_pkgs/affine-shared/services/feature-flag-service.d.ts +4 -0
- package/dist/_pkgs/affine-shared/services/index.d.ts +3 -0
- package/dist/_pkgs/affine-shared/services/index.js +3 -0
- package/dist/_pkgs/affine-shared/services/selection-pane-service.d.ts +44 -0
- package/dist/_pkgs/affine-shared/services/selection-pane-service.js +28 -0
- package/dist/_pkgs/affine-shared/services/telemetry-service/lifecycle.d.ts +69 -0
- package/dist/_pkgs/affine-shared/services/telemetry-service/telemetry-service.d.ts +2 -2
- package/dist/_pkgs/affine-shared/services/translation-service/chrome.d.ts +5 -0
- package/dist/_pkgs/affine-shared/services/translation-service/chrome.js +9 -0
- package/dist/_pkgs/affine-shared/styles/index.d.ts +1 -0
- package/dist/_pkgs/affine-shared/styles/index.js +1 -0
- package/dist/_pkgs/affine-shared/styles/panel-header.d.ts +31 -0
- package/dist/_pkgs/affine-shared/styles/panel-header.js +61 -0
- package/dist/_pkgs/affine-shared/styles/text.js +7 -7
- package/dist/_pkgs/affine-shared/types/index.d.ts +6 -0
- package/dist/_pkgs/affine-shared/utils/canvas-export-colors.d.ts +26 -0
- package/dist/_pkgs/affine-shared/utils/canvas-export-colors.js +127 -0
- package/dist/_pkgs/affine-shared/utils/file/filesys.d.ts +8 -11
- package/dist/_pkgs/affine-shared/utils/file/filesys.js +8 -11
- package/dist/_pkgs/affine-shared/utils/index.d.ts +2 -0
- package/dist/_pkgs/affine-shared/utils/index.js +2 -0
- package/dist/_pkgs/affine-shared/utils/label-mode.d.ts +47 -0
- package/dist/_pkgs/affine-shared/utils/label-mode.js +55 -0
- package/dist/_pkgs/affine-shared/utils/model/merge-to-code-model.js +7 -1
- package/dist/_pkgs/affine-shared/utils/model/transform-model.js +5 -0
- package/dist/_pkgs/affine-widget-edgeless-selected-rect/utils.js +10 -3
- package/dist/_pkgs/affine-widget-edgeless-toolbar/catalogue/artefact-catalogue-widget.js +25 -49
- package/dist/_pkgs/affine-widget-edgeless-toolbar/effects.d.ts +4 -0
- package/dist/_pkgs/affine-widget-edgeless-toolbar/effects.js +4 -0
- package/dist/_pkgs/affine-widget-edgeless-toolbar/index.d.ts +4 -0
- package/dist/_pkgs/affine-widget-edgeless-toolbar/index.js +4 -0
- package/dist/_pkgs/affine-widget-edgeless-toolbar/selection-pane/drop.d.ts +61 -0
- package/dist/_pkgs/affine-widget-edgeless-toolbar/selection-pane/drop.js +91 -0
- package/dist/_pkgs/affine-widget-edgeless-toolbar/selection-pane/labels.d.ts +17 -0
- package/dist/_pkgs/affine-widget-edgeless-toolbar/selection-pane/labels.js +95 -0
- package/dist/_pkgs/affine-widget-edgeless-toolbar/selection-pane/selection-pane-default.d.ts +10 -0
- package/dist/_pkgs/affine-widget-edgeless-toolbar/selection-pane/selection-pane-default.js +31 -0
- package/dist/_pkgs/affine-widget-edgeless-toolbar/selection-pane/selection-pane-tool.d.ts +26 -0
- package/dist/_pkgs/affine-widget-edgeless-toolbar/selection-pane/selection-pane-tool.js +82 -0
- package/dist/_pkgs/affine-widget-edgeless-toolbar/selection-pane/selection-pane-widget.d.ts +170 -0
- package/dist/_pkgs/affine-widget-edgeless-toolbar/selection-pane/selection-pane-widget.js +1381 -0
- package/dist/_pkgs/affine-widget-edgeless-toolbar/translations.d.ts +52 -0
- package/dist/_pkgs/affine-widget-edgeless-toolbar/translations.js +161 -1
- package/dist/_pkgs/affine-widget-edgeless-toolbar/view.js +10 -0
- package/dist/_pkgs/affine-widget-note-slicer/note-slicer.js +7 -3
- package/dist/_pkgs/std/gfx/controller.d.ts +13 -0
- package/dist/_pkgs/std/gfx/controller.js +22 -2
- package/dist/_pkgs/std/gfx/grid.d.ts +31 -2
- package/dist/_pkgs/std/gfx/index.d.ts +3 -1
- package/dist/_pkgs/std/gfx/index.js +3 -1
- package/dist/_pkgs/std/gfx/interactivity/manager.js +7 -0
- package/dist/_pkgs/std/gfx/layer.js +73 -5
- package/dist/_pkgs/std/gfx/local-visibility.d.ts +88 -0
- package/dist/_pkgs/std/gfx/local-visibility.js +217 -0
- package/dist/_pkgs/std/gfx/model/gfx-block-model.d.ts +13 -0
- package/dist/_pkgs/std/gfx/model/surface/element-model.d.ts +34 -0
- package/dist/_pkgs/std/gfx/model/surface/element-model.js +65 -1
- package/dist/_pkgs/std/gfx/model/surface/surface-model.d.ts +27 -0
- package/dist/_pkgs/std/gfx/model/surface/surface-model.js +43 -0
- package/dist/_pkgs/std/gfx/model/surface/user-layers.d.ts +68 -0
- package/dist/_pkgs/std/gfx/model/surface/user-layers.js +127 -0
- package/dist/_pkgs/std/utils/layer.d.ts +10 -0
- package/dist/_pkgs/std/utils/layer.js +64 -13
- package/dist/_pkgs/std/view/element/gfx-block-component.js +10 -2
- package/dist/commands.js +4 -1
- package/dist/translations.js +10 -6
- package/package.json +9 -2
- package/dist/_pkgs/affine-components/icons/file-icons-rc.d.ts +0 -1
- package/dist/_pkgs/affine-components/icons/file-icons-rc.js +0 -130
- package/dist/_pkgs/affine-shared/test-utils/affine-template.d.ts +0 -6
- package/dist/_pkgs/affine-shared/test-utils/affine-template.js +0 -258
- package/dist/_pkgs/affine-shared/test-utils/affine-test-utils.d.ts +0 -8
- package/dist/_pkgs/affine-shared/test-utils/affine-test-utils.js +0 -81
- package/dist/_pkgs/affine-shared/test-utils/create-test-host.d.ts +0 -23
- package/dist/_pkgs/affine-shared/test-utils/create-test-host.js +0 -187
- package/dist/_pkgs/affine-shared/test-utils/index.d.ts +0 -3
- package/dist/_pkgs/affine-shared/test-utils/index.js +0 -3
|
@@ -30,8 +30,7 @@
|
|
|
30
30
|
import { getAuditCriteria, requestAudit, TelemetryProvider, } from '../../affine-shared/services/index.js';
|
|
31
31
|
import { GfxControllerIdentifier, GfxPrimitiveElementModel, roleIsA, } from '../../std/gfx/index.js';
|
|
32
32
|
import { z } from 'zod';
|
|
33
|
-
import {
|
|
34
|
-
import { backgroundAxisFacts, containingFrame, } from '../framework-background/facts.js';
|
|
33
|
+
import { backgroundAxisFacts, backgroundPlotRatios, backgroundZoneAt, backgroundZones, containingFrame, } from '../framework-background/facts.js';
|
|
35
34
|
import { ValidationManager, ValidationRuleIdentifier, } from './validation.js';
|
|
36
35
|
/**
|
|
37
36
|
* `map.audit` takes no required parameter: the assistant audits what is
|
|
@@ -113,69 +112,21 @@ function collectFrames(rules, elements) {
|
|
|
113
112
|
type: def.type,
|
|
114
113
|
...(typeof profileId === 'string' ? { profileId } : {}),
|
|
115
114
|
axes: backgroundAxisFacts(def),
|
|
116
|
-
// The framework's
|
|
117
|
-
// a BPMN pool's lanes
|
|
118
|
-
//
|
|
119
|
-
//
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
rect: { ...zone.rect },
|
|
126
|
-
})),
|
|
127
|
-
...backgroundInstanceZones(def, el).map(zone => ({
|
|
128
|
-
id: zone.id,
|
|
129
|
-
...(zone.name !== undefined ? { name: zone.name } : {}),
|
|
130
|
-
rect: { ...zone.rect },
|
|
131
|
-
})),
|
|
132
|
-
],
|
|
115
|
+
// The zones THIS frame has — the framework's, in the variant it is
|
|
116
|
+
// turned to, then its own (a BPMN pool's lanes) — read through the
|
|
117
|
+
// helper the reading panel uses, so the two cannot disagree. Copied
|
|
118
|
+
// field by field: the declared label is painting data, not a fact.
|
|
119
|
+
zones: backgroundZones(def, el).map(zone => ({
|
|
120
|
+
id: zone.id,
|
|
121
|
+
...(zone.name !== undefined ? { name: zone.name } : {}),
|
|
122
|
+
rect: { ...zone.rect },
|
|
123
|
+
})),
|
|
133
124
|
},
|
|
134
125
|
});
|
|
135
126
|
}
|
|
136
127
|
}
|
|
137
128
|
return frames;
|
|
138
129
|
}
|
|
139
|
-
/**
|
|
140
|
-
* Where an element's centre sits inside a frame's PLOT, as ratios.
|
|
141
|
-
*
|
|
142
|
-
* A POSITION, not a membership test: it is asked only about an element some
|
|
143
|
-
* frame already contains, and answers where in that frame's plot it lies.
|
|
144
|
-
*
|
|
145
|
-
* Ratios of the plot and not of the element box: a Wardley transition drawn at
|
|
146
|
-
* `0.4` is 40 % of the PLOT, not of the map element, and the margin between the
|
|
147
|
-
* two is exactly where the axis titles live. `backgroundPlot` is the one place
|
|
148
|
-
* that knows the difference, and this is the only reason this function exists
|
|
149
|
-
* rather than a subtraction at the call site.
|
|
150
|
-
*
|
|
151
|
-
* Not clamped: an element just off the left edge reads as `-0.03`, which is a
|
|
152
|
-
* true and useful thing to say. `null` for a degenerate plot.
|
|
153
|
-
*/
|
|
154
|
-
function plotRatios(frame, bound) {
|
|
155
|
-
const plot = backgroundPlot(frame.def, frame.bound.w, frame.bound.h);
|
|
156
|
-
if (!(plot.width > 0) || !(plot.height > 0))
|
|
157
|
-
return null;
|
|
158
|
-
const cx = bound.x + bound.w / 2;
|
|
159
|
-
const cy = bound.y + bound.h / 2;
|
|
160
|
-
return [
|
|
161
|
-
(cx - frame.bound.x - plot.x0) / plot.width,
|
|
162
|
-
(cy - frame.bound.y - plot.y0) / plot.height,
|
|
163
|
-
];
|
|
164
|
-
}
|
|
165
|
-
/**
|
|
166
|
-
* The zone a plot-ratio point falls in, if any — one the framework declares or
|
|
167
|
-
* one the frame itself does. It needs to know nothing about the difference: the
|
|
168
|
-
* fact carries both, in that order, as rectangles in the same ratios.
|
|
169
|
-
*/
|
|
170
|
-
function zoneAt(frame, at) {
|
|
171
|
-
for (const zone of frame.fact.zones) {
|
|
172
|
-
const { x, y, w, h } = zone.rect;
|
|
173
|
-
if (at[0] >= x && at[0] <= x + w && at[1] >= y && at[1] <= y + h) {
|
|
174
|
-
return zone.id;
|
|
175
|
-
}
|
|
176
|
-
}
|
|
177
|
-
return undefined;
|
|
178
|
-
}
|
|
179
130
|
/**
|
|
180
131
|
* Levels 1 and 2, copied out of the engine's verdict.
|
|
181
132
|
*
|
|
@@ -245,8 +196,9 @@ export function collectAuditFacts(std) {
|
|
|
245
196
|
elementFacts.push({ id: el.id, role });
|
|
246
197
|
continue;
|
|
247
198
|
}
|
|
248
|
-
|
|
249
|
-
const
|
|
199
|
+
// A POSITION, not a membership test: `frame` already contains the element.
|
|
200
|
+
const at = backgroundPlotRatios(frame.def, frame.bound, bound);
|
|
201
|
+
const zone = at === null ? undefined : backgroundZoneAt(frame.fact.zones, at)?.id;
|
|
250
202
|
elementFacts.push({
|
|
251
203
|
id: el.id,
|
|
252
204
|
role,
|
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
import { CanvasGrid, TelemetryProvider } from '../../../affine-shared/services/index.js';
|
|
2
|
+
/**
|
|
3
|
+
* The canvas grid's two commands (ADR 0031 §11, §12), `owner: 'core'`, on the
|
|
4
|
+
* palette and the agent. The library has no page "more" menu — that belongs
|
|
5
|
+
* to the host — so these are the grid's whole UI here; a host puts them in
|
|
6
|
+
* its own menu through `runCommand`.
|
|
7
|
+
*
|
|
8
|
+
* Both self-emit `CanvasGridToggled` (see the telemetry README): `scope` is
|
|
9
|
+
* which gesture ran, and a save that changes nothing reports nothing.
|
|
10
|
+
*/
|
|
11
|
+
function reportGrid(std, scope, visible) {
|
|
12
|
+
std.getOptional(TelemetryProvider)?.track('CanvasGridToggled', {
|
|
13
|
+
page: 'whiteboard editor',
|
|
14
|
+
scope,
|
|
15
|
+
visible,
|
|
16
|
+
});
|
|
17
|
+
}
|
|
18
|
+
/**
|
|
19
|
+
* Show or hide the grid for THIS viewer, on this document. Writes nothing to
|
|
20
|
+
* the document, so a reader may do it too.
|
|
21
|
+
*/
|
|
22
|
+
const toggleGrid = {
|
|
23
|
+
id: 'canvas.grid.toggle',
|
|
24
|
+
owner: 'core',
|
|
25
|
+
kind: 'action',
|
|
26
|
+
labelKey: 'com.labre.command.canvas.grid.toggle',
|
|
27
|
+
labelFallback: 'Show or hide the grid',
|
|
28
|
+
descriptionKey: 'com.labre.command.canvas.grid.toggle.description',
|
|
29
|
+
descriptionFallback: 'Show or hide the canvas grid on your screen only. Nothing changes for anyone else.',
|
|
30
|
+
keywords: ['grid', 'dots', 'background'],
|
|
31
|
+
surfaces: ['palette', 'agent'],
|
|
32
|
+
scope: 'edgeless',
|
|
33
|
+
defaultKeys: { mac: [], other: [] },
|
|
34
|
+
when: std => !!std.getOptional(CanvasGrid),
|
|
35
|
+
run: std => {
|
|
36
|
+
const grid = std.getOptional(CanvasGrid);
|
|
37
|
+
if (!grid)
|
|
38
|
+
return;
|
|
39
|
+
reportGrid(std, 'local', grid.toggle());
|
|
40
|
+
},
|
|
41
|
+
};
|
|
42
|
+
/**
|
|
43
|
+
* Store the grid as this viewer sees it on the document, for everyone, and
|
|
44
|
+
* drop this viewer's own override. Read-only refuses (`availability`, and
|
|
45
|
+
* again in `CanvasGrid.saveForEveryone`).
|
|
46
|
+
*/
|
|
47
|
+
const saveGridForEveryone = {
|
|
48
|
+
id: 'canvas.grid.saveForEveryone',
|
|
49
|
+
owner: 'core',
|
|
50
|
+
kind: 'action',
|
|
51
|
+
labelKey: 'com.labre.command.canvas.grid.save-for-everyone',
|
|
52
|
+
labelFallback: 'Save the grid for everyone',
|
|
53
|
+
descriptionKey: 'com.labre.command.canvas.grid.save-for-everyone.description',
|
|
54
|
+
descriptionFallback: 'Make the grid as you see it now the setting of this document, for everyone who opens it.',
|
|
55
|
+
keywords: ['grid', 'dots', 'background', 'document'],
|
|
56
|
+
surfaces: ['palette', 'agent'],
|
|
57
|
+
scope: 'edgeless',
|
|
58
|
+
defaultKeys: { mac: [], other: [] },
|
|
59
|
+
availability: 'editable',
|
|
60
|
+
when: std => !!std.getOptional(CanvasGrid),
|
|
61
|
+
run: std => {
|
|
62
|
+
const saved = std.getOptional(CanvasGrid)?.saveForEveryone() ?? null;
|
|
63
|
+
if (saved === null)
|
|
64
|
+
return;
|
|
65
|
+
reportGrid(std, 'everyone', saved);
|
|
66
|
+
},
|
|
67
|
+
};
|
|
68
|
+
export const canvasGridCommands = [
|
|
69
|
+
toggleGrid,
|
|
70
|
+
saveGridForEveryone,
|
|
71
|
+
];
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { canvasGridCommands } from './commands.js';
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { canvasGridCommands } from './commands.js';
|
|
@@ -4,12 +4,16 @@ import { StdIdentifier } from '../../std/index.js';
|
|
|
4
4
|
import { Extension } from '../../store/index.js';
|
|
5
5
|
import { getSurfaceComponent } from '../utils/get-surface-block.js';
|
|
6
6
|
import { EdgelessCRUDIdentifier } from './crud-extension.js';
|
|
7
|
+
import { applyCreationLayer } from './user-layers/creation.js';
|
|
7
8
|
export const EdgelessClipboardConfigIdentifier = createIdentifier('edgeless-clipboard-config');
|
|
8
9
|
export class EdgelessClipboardConfig extends Extension {
|
|
9
10
|
constructor(std) {
|
|
10
11
|
super();
|
|
11
12
|
this.std = std;
|
|
12
13
|
this.onBlockSnapshotPaste = async (snapshot, doc, parent, index) => {
|
|
14
|
+
// The clipboard's block path follows the elements' rule (ADR 0031 §6):
|
|
15
|
+
// a layer of this surface is kept, anything else lands in the active one.
|
|
16
|
+
applyCreationLayer(this.std, snapshot.props);
|
|
13
17
|
const block = await this.std.clipboard.pasteBlockSnapshot(snapshot, doc, parent, index);
|
|
14
18
|
return block?.id ?? null;
|
|
15
19
|
};
|
|
@@ -5,6 +5,7 @@ import { GfxBlockElementModel, GfxControllerIdentifier, isGfxGroupCompatibleMode
|
|
|
5
5
|
import { Extension } from '../../store/index.js';
|
|
6
6
|
import { getLastPropsKey } from '../utils/get-last-props-key.js';
|
|
7
7
|
import { isConnectable, isNoteBlock } from './query.js';
|
|
8
|
+
import { applyCreationLayer } from './user-layers/creation.js';
|
|
8
9
|
export const EdgelessCRUDIdentifier = createIdentifier('AffineEdgelessCrudService');
|
|
9
10
|
export class EdgelessCRUDExtension extends Extension {
|
|
10
11
|
constructor(std) {
|
|
@@ -48,6 +49,9 @@ export class EdgelessCRUDExtension extends Extension {
|
|
|
48
49
|
...props,
|
|
49
50
|
index: gfx.layer.generateIndex(),
|
|
50
51
|
};
|
|
52
|
+
// A gfx block gets the elements' rule (ADR 0031 §6): its own layer if it
|
|
53
|
+
// names one of this surface, else the viewer's active layer.
|
|
54
|
+
applyCreationLayer(this.std, nProps);
|
|
51
55
|
return this.std.store.addBlock(flavour, nProps, parentId, parentIndex);
|
|
52
56
|
};
|
|
53
57
|
this.addElement = (type, props) => {
|
|
@@ -3,6 +3,18 @@ import { type BlockStdScope, type EditorHost } from '../../../std/index.js';
|
|
|
3
3
|
import { GfxBlockElementModel, type GfxController, GfxPrimitiveElementModel } from '../../../std/gfx/index.js';
|
|
4
4
|
import type { ExtensionType, Store } from '../../../store/index.js';
|
|
5
5
|
import { CanvasRenderer } from '../../renderer/canvas-renderer.js';
|
|
6
|
+
export type EdgelessBackgroundOptions = {
|
|
7
|
+
size: number;
|
|
8
|
+
backgroundColor: string;
|
|
9
|
+
/** `null` when the grid is off (ADR 0031 §11): the background alone. */
|
|
10
|
+
gridColor: string | null;
|
|
11
|
+
};
|
|
12
|
+
/**
|
|
13
|
+
* The SVG the PNG export paints the canvas background from: the background
|
|
14
|
+
* colour, plus the dotted grid unless `gridColor` is `null` — what this
|
|
15
|
+
* viewer sees, as `CanvasGrid.visible$` says.
|
|
16
|
+
*/
|
|
17
|
+
export declare function edgelessBackgroundSvg(width: number, height: number, { size, backgroundColor, gridColor }: EdgelessBackgroundOptions): string;
|
|
6
18
|
export declare class ExportManager {
|
|
7
19
|
readonly std: BlockStdScope;
|
|
8
20
|
/**
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import { ImageBlockModel } from '../../../affine-model/index.js';
|
|
2
2
|
import { FetchUtils, ImageProxyService } from '../../../affine-shared/adapters/index.js';
|
|
3
3
|
import { CANVAS_EXPORT_IGNORE_TAGS } from '../../../affine-shared/consts/index.js';
|
|
4
|
-
import { CHROME_UNTITLED, translateKey } from '../../../affine-shared/services/index.js';
|
|
5
|
-
import { isInsidePageEditor, matchModels } from '../../../affine-shared/utils/index.js';
|
|
4
|
+
import { CanvasGrid, CHROME_UNTITLED, translateKey, } from '../../../affine-shared/services/index.js';
|
|
5
|
+
import { isInsidePageEditor, matchModels, normalizeCanvasExportColors, toLegacyColors, } from '../../../affine-shared/utils/index.js';
|
|
6
6
|
import { BlockSuiteError, ErrorCode } from '../../../global/exceptions/index.js';
|
|
7
7
|
import { deserializeXYWH } from '../../../global/gfx/index.js';
|
|
8
8
|
import { StdIdentifier, } from '../../../std/index.js';
|
|
@@ -10,6 +10,17 @@ import { GfxBlockElementModel, GfxControllerIdentifier, GfxPrimitiveElementModel
|
|
|
10
10
|
import { CanvasRenderer } from '../../renderer/canvas-renderer.js';
|
|
11
11
|
import { getBgGridGap } from '../../utils/get-bg-grip-gap.js';
|
|
12
12
|
import { FileExporter } from './file-exporter.js';
|
|
13
|
+
/**
|
|
14
|
+
* The SVG the PNG export paints the canvas background from: the background
|
|
15
|
+
* colour, plus the dotted grid unless `gridColor` is `null` — what this
|
|
16
|
+
* viewer sees, as `CanvasGrid.visible$` says.
|
|
17
|
+
*/
|
|
18
|
+
export function edgelessBackgroundSvg(width, height, { size, backgroundColor, gridColor }) {
|
|
19
|
+
const grid = gridColor === null
|
|
20
|
+
? ''
|
|
21
|
+
: ` background-image: radial-gradient(${gridColor} 1px, ${backgroundColor} 1px)`;
|
|
22
|
+
return `<svg width='${width}px' height='${height}px' xmlns='http://www.w3.org/2000/svg' style='background-size:${size}px ${size}px;background-color:${backgroundColor};${grid}'></svg>`;
|
|
23
|
+
}
|
|
13
24
|
export class ExportManager {
|
|
14
25
|
/**
|
|
15
26
|
* The image proxy every remote-image fetch of the export goes through —
|
|
@@ -157,11 +168,12 @@ export class ExportManager {
|
|
|
157
168
|
return false;
|
|
158
169
|
}
|
|
159
170
|
},
|
|
160
|
-
onclone: async (
|
|
171
|
+
onclone: async (documentClone, element) => {
|
|
172
|
+
normalizeCanvasExportColors(documentClone, element);
|
|
161
173
|
element.style.height = `${viewportHeight}px`;
|
|
162
174
|
await this.replaceImgSrcWithSvg(element);
|
|
163
175
|
},
|
|
164
|
-
backgroundColor: window.getComputedStyle(viewportElement).backgroundColor,
|
|
176
|
+
backgroundColor: toLegacyColors(window.getComputedStyle(viewportElement).backgroundColor),
|
|
165
177
|
x: pageLeft - viewport.left,
|
|
166
178
|
width: pageWidth,
|
|
167
179
|
height: viewportHeight,
|
|
@@ -179,8 +191,8 @@ export class ExportManager {
|
|
|
179
191
|
this._checkCanContinueToCanvas(pathname, editorMode);
|
|
180
192
|
return data;
|
|
181
193
|
}
|
|
182
|
-
_drawEdgelessBackground(ctx,
|
|
183
|
-
const svgImg =
|
|
194
|
+
_drawEdgelessBackground(ctx, options) {
|
|
195
|
+
const svgImg = edgelessBackgroundSvg(ctx.canvas.width, ctx.canvas.height, options);
|
|
184
196
|
const img = new Image();
|
|
185
197
|
const cleanup = () => {
|
|
186
198
|
img.onload = null;
|
|
@@ -218,6 +230,7 @@ export class ExportManager {
|
|
|
218
230
|
}
|
|
219
231
|
},
|
|
220
232
|
onclone: async (documentClone, element) => {
|
|
233
|
+
normalizeCanvasExportColors(documentClone, element);
|
|
221
234
|
// html2canvas can't support transform feature
|
|
222
235
|
element.style.setProperty('transform', 'none');
|
|
223
236
|
const layer = element.classList.contains('.affine-edgeless-layer')
|
|
@@ -300,7 +313,10 @@ export class ExportManager {
|
|
|
300
313
|
await this._drawEdgelessBackground(ctx, {
|
|
301
314
|
backgroundColor: containerComputedStyle.getPropertyValue('--affine-background-primary-color'),
|
|
302
315
|
size: getBgGridGap(edgelessBackground.zoom),
|
|
303
|
-
|
|
316
|
+
// What this viewer sees: off leaves the background colour alone.
|
|
317
|
+
gridColor: (this.std.getOptional(CanvasGrid)?.visible$.peek() ?? true)
|
|
318
|
+
? containerComputedStyle.getPropertyValue('--affine-edgeless-grid-color')
|
|
319
|
+
: null,
|
|
304
320
|
});
|
|
305
321
|
}
|
|
306
322
|
if (!blocks && !elements) {
|
|
@@ -331,6 +347,10 @@ export class ExportManager {
|
|
|
331
347
|
elements = [...elementSet];
|
|
332
348
|
blocks = [...blockSet];
|
|
333
349
|
}
|
|
350
|
+
// What you see is what you export (ADR 0031, resolved at acceptance): a
|
|
351
|
+
// block this viewer hid is not drawn. Canvas elements are left out by the
|
|
352
|
+
// renderer's own paint predicate.
|
|
353
|
+
blocks = blocks.filter(block => !gfx.localVisibility.isHidden(block));
|
|
334
354
|
for (const block of blocks) {
|
|
335
355
|
if (matchModels(block, [ImageBlockModel])) {
|
|
336
356
|
if (!block.props.sourceId)
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { FrameworkBackgroundElementModel } from '../../../affine-model/index.js';
|
|
2
2
|
import type { AnyCommandDescriptor, BlockStdScope } from '../../../std/index.js';
|
|
3
|
+
import { type BoardSvgExportOptions } from './parts.js';
|
|
3
4
|
/**
|
|
4
5
|
* The framework boards in the current canvas selection.
|
|
5
6
|
*
|
|
@@ -19,5 +20,5 @@ export declare function selectedBoards(std: BlockStdScope): FrameworkBackgroundE
|
|
|
19
20
|
* on the browser — a result nobody can read off the gesture. One board, one
|
|
20
21
|
* file, every time.
|
|
21
22
|
*/
|
|
22
|
-
export declare function exportBoardSvg(std: BlockStdScope): void;
|
|
23
|
+
export declare function exportBoardSvg(std: BlockStdScope, options?: Readonly<BoardSvgExportOptions>): void;
|
|
23
24
|
export declare const exportSvgCommands: AnyCommandDescriptor[];
|
|
@@ -1,7 +1,10 @@
|
|
|
1
1
|
import { FrameworkBackgroundElementModel } from '../../../affine-model/index.js';
|
|
2
|
+
import { NotificationProvider, translateKey, } from '../../../affine-shared/services/index.js';
|
|
2
3
|
import { downloadBlob, safeFilename } from '../../../affine-shared/utils/index.js';
|
|
3
4
|
import { GfxControllerIdentifier } from '../../../std/gfx/index.js';
|
|
5
|
+
import { boardSvgExportOptions, DEFAULT_BOARD_SVG_EXPORT_OPTIONS, } from './parts.js';
|
|
4
6
|
import { renderBoardSvg } from './render.js';
|
|
7
|
+
import { EXPORT_SVG_NOTHING_TO_EXPORT } from './translations.js';
|
|
5
8
|
/** What the file is, told to the browser. */
|
|
6
9
|
const SVG_MIME = 'image/svg+xml';
|
|
7
10
|
/** The name a board with no document title falls back to. */
|
|
@@ -29,11 +32,20 @@ export function selectedBoards(std) {
|
|
|
29
32
|
* on the browser — a result nobody can read off the gesture. One board, one
|
|
30
33
|
* file, every time.
|
|
31
34
|
*/
|
|
32
|
-
export function exportBoardSvg(std) {
|
|
35
|
+
export function exportBoardSvg(std, options = DEFAULT_BOARD_SVG_EXPORT_OPTIONS) {
|
|
33
36
|
const [board] = selectedBoards(std);
|
|
34
37
|
if (!board)
|
|
35
38
|
return;
|
|
36
|
-
const
|
|
39
|
+
const rendered = renderBoardSvg(std, board, options);
|
|
40
|
+
if (!rendered) {
|
|
41
|
+
// Every part left was switched off. Said once, through the host's
|
|
42
|
+
// notification seam; a host without one simply gets no file.
|
|
43
|
+
std
|
|
44
|
+
.getOptional(NotificationProvider)
|
|
45
|
+
?.toast(translateKey(std, ...EXPORT_SVG_NOTHING_TO_EXPORT));
|
|
46
|
+
return;
|
|
47
|
+
}
|
|
48
|
+
const { svg } = rendered;
|
|
37
49
|
const title = std.store.workspace.meta.getDocMeta(std.store.id)?.title;
|
|
38
50
|
downloadBlob(
|
|
39
51
|
// The charset is the browser's business, not the format's: `image/svg+xml`
|
|
@@ -53,6 +65,13 @@ export function exportBoardSvg(std) {
|
|
|
53
65
|
* It READS, so there is no read-only guard: taking a picture of a board you
|
|
54
66
|
* cannot edit is precisely what a reader does.
|
|
55
67
|
*
|
|
68
|
+
* Its optional params are the export options (`parts.ts`), which the "⋮"
|
|
69
|
+
* entry asks for before it runs this. Every other surface — the palette, the
|
|
70
|
+
* catalogue, a shortcut, the agent — passes nothing and exports everything,
|
|
71
|
+
* without a dialog. They are deliberately not declared as `params`: the agent
|
|
72
|
+
* contract stays "export the selected board", and `run` re-validates whatever
|
|
73
|
+
* arrives.
|
|
74
|
+
*
|
|
56
75
|
* No `telemetry` field: `CommandTelemetry.framework` is typed on `FrameworkId`,
|
|
57
76
|
* and this command cannot name one — the surface package knows a board by its
|
|
58
77
|
* MODEL CLASS, and nothing in it maps `bpmnPool` back to `bpmn` without
|
|
@@ -84,6 +103,6 @@ const exportSvg = {
|
|
|
84
103
|
// union can express.
|
|
85
104
|
availability: 'selection:framework',
|
|
86
105
|
when: std => selectedBoards(std).length > 0,
|
|
87
|
-
run: std => exportBoardSvg(std),
|
|
106
|
+
run: (std, _invocation, params) => exportBoardSvg(std, boardSvgExportOptions(params)),
|
|
88
107
|
};
|
|
89
108
|
export const exportSvgCommands = [exportSvg];
|
|
@@ -1,7 +1,10 @@
|
|
|
1
1
|
export { exportBoardSvg, exportSvgCommands, selectedBoards, } from './command.js';
|
|
2
|
-
export type {
|
|
3
|
-
export {
|
|
2
|
+
export type { BoardSvgExportOptions, BoardSvgExportPart, SvgExportCandidate, } from './parts.js';
|
|
3
|
+
export { boardSvgExportOptions, boardSvgExportPartOf, DEFAULT_BOARD_SVG_EXPORT_OPTIONS, selectBoardSvgParts, } from './parts.js';
|
|
4
|
+
export type { BlockSvgPainter, BoardSvgExport } from './render.js';
|
|
5
|
+
export { BlockSvgPainterExtension, BlockSvgPainterIdentifier, boardSvgMarkers, exportBoundOf, renderBoardSvg, selectBoardElements, } from './render.js';
|
|
4
6
|
export { taggedPath2D } from './tagged-path.js';
|
|
5
7
|
export type { SvgContext } from './svg-context.js';
|
|
6
|
-
export { createSvgContext, runWithRecordingPath2D } from './svg-context.js';
|
|
8
|
+
export { BOARD_SVG_MARKER_VERSION, createSvgContext, runWithRecordingPath2D, } from './svg-context.js';
|
|
7
9
|
export { exportSvgToolbarConfig, exportSvgToolbarExtension, } from './toolbar.js';
|
|
10
|
+
export { EXPORT_SVG_WORDINGS } from './translations.js';
|
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
export { exportBoardSvg, exportSvgCommands, selectedBoards, } from './command.js';
|
|
2
|
-
export {
|
|
2
|
+
export { boardSvgExportOptions, boardSvgExportPartOf, DEFAULT_BOARD_SVG_EXPORT_OPTIONS, selectBoardSvgParts, } from './parts.js';
|
|
3
|
+
export { BlockSvgPainterExtension, BlockSvgPainterIdentifier, boardSvgMarkers, exportBoundOf, renderBoardSvg, selectBoardElements, } from './render.js';
|
|
3
4
|
export { taggedPath2D } from './tagged-path.js';
|
|
4
|
-
export { createSvgContext, runWithRecordingPath2D } from './svg-context.js';
|
|
5
|
+
export { BOARD_SVG_MARKER_VERSION, createSvgContext, runWithRecordingPath2D, } from './svg-context.js';
|
|
5
6
|
export { exportSvgToolbarConfig, exportSvgToolbarExtension, } from './toolbar.js';
|
|
7
|
+
export { EXPORT_SVG_WORDINGS } from './translations.js';
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* What "Export SVG" puts in the file — the three switches of its options menu,
|
|
3
|
+
* all on by default (ADR 0025, amendment of 2026-10-04).
|
|
4
|
+
*/
|
|
5
|
+
export interface BoardSvgExportOptions {
|
|
6
|
+
/** The board, its framework's artefacts and its generated legend. */
|
|
7
|
+
framework: boolean;
|
|
8
|
+
/** Every other canvas element that is not a text: shapes, connectors, strokes. */
|
|
9
|
+
shapes: boolean;
|
|
10
|
+
/** Every other text: canvas texts, and the edgeless text blocks. */
|
|
11
|
+
texts: boolean;
|
|
12
|
+
}
|
|
13
|
+
export type BoardSvgExportPart = keyof BoardSvgExportOptions;
|
|
14
|
+
export declare const DEFAULT_BOARD_SVG_EXPORT_OPTIONS: Readonly<BoardSvgExportOptions>;
|
|
15
|
+
/**
|
|
16
|
+
* The options a command invocation carries, re-validated: the palette and the
|
|
17
|
+
* agent pass nothing and get everything, and only an explicit `false` switches
|
|
18
|
+
* a part off — a stray value never empties a file.
|
|
19
|
+
*/
|
|
20
|
+
export declare function boardSvgExportOptions(params: unknown): BoardSvgExportOptions;
|
|
21
|
+
/**
|
|
22
|
+
* The stored facts the rule reads, and nothing else: an element's `role` and
|
|
23
|
+
* `type`, and a group's `childElements`. Structural, so the rule runs over a
|
|
24
|
+
* real model and over a recorded creation alike.
|
|
25
|
+
*/
|
|
26
|
+
export interface SvgExportCandidate {
|
|
27
|
+
readonly role?: string;
|
|
28
|
+
readonly type?: string;
|
|
29
|
+
readonly childElements?: readonly SvgExportCandidate[];
|
|
30
|
+
}
|
|
31
|
+
/**
|
|
32
|
+
* Which switch an element on `board` answers to.
|
|
33
|
+
*
|
|
34
|
+
* - **Framework elements**: the board itself; anything whose role shares the
|
|
35
|
+
* board's role namespace (`wardley:map` owns `wardley:component`,
|
|
36
|
+
* `wardley:label`, `wardley:dependency`…); the generated legend
|
|
37
|
+
* (`core:legend`, ADR 0026) and every glyph in it; and a ROLE-LESS element
|
|
38
|
+
* grouped with any of those. The last clause is what a framework artefact is
|
|
39
|
+
* made of: an EDGY person and its name, a Wardley market and its three dots,
|
|
40
|
+
* a Core Domain sub-domain and its title are one group in which only one
|
|
41
|
+
* member carries the role.
|
|
42
|
+
* - **Other texts**: any other `text` element — a plain one, or one of ANOTHER
|
|
43
|
+
* framework lying on this board, which is a text like any other here.
|
|
44
|
+
* - **Other shapes and strokes**: everything else — plain shapes, plain
|
|
45
|
+
* connectors, brush and highlighter strokes, mind maps, another framework's
|
|
46
|
+
* shapes, and a plain group (which paints nothing of its own in an export).
|
|
47
|
+
*
|
|
48
|
+
* Read off the namespace rather than a `FrameworkId` on purpose: three DDD
|
|
49
|
+
* frameworks spell their roles `es:`, `core-domain:` and `context-map:`, and
|
|
50
|
+
* the board says which one it speaks. A board with no role (Cynefin, which
|
|
51
|
+
* paints its domains itself) owns itself and nothing else. Edgeless text
|
|
52
|
+
* BLOCKS never reach this function: they carry no role and are always "other
|
|
53
|
+
* texts" ({@link selectBoardSvgParts}).
|
|
54
|
+
*/
|
|
55
|
+
export declare function boardSvgExportPartOf(board: SvgExportCandidate, element: SvgExportCandidate, groups: readonly SvgExportCandidate[]): BoardSvgExportPart;
|
|
56
|
+
/**
|
|
57
|
+
* What the file draws under `options`: the canvas elements, in the paint order
|
|
58
|
+
* they came in, and the edgeless text blocks, which are all "other texts".
|
|
59
|
+
*/
|
|
60
|
+
export declare function selectBoardSvgParts<E extends SvgExportCandidate, B>(board: SvgExportCandidate, elements: readonly E[], textBlocks: readonly B[], options: Readonly<BoardSvgExportOptions>, groupsOf: (element: E) => readonly SvgExportCandidate[]): {
|
|
61
|
+
elements: E[];
|
|
62
|
+
textBlocks: B[];
|
|
63
|
+
};
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
import { LEGEND_ROLE } from '../legend.js';
|
|
2
|
+
export const DEFAULT_BOARD_SVG_EXPORT_OPTIONS = Object.freeze({ framework: true, shapes: true, texts: true });
|
|
3
|
+
/**
|
|
4
|
+
* The options a command invocation carries, re-validated: the palette and the
|
|
5
|
+
* agent pass nothing and get everything, and only an explicit `false` switches
|
|
6
|
+
* a part off — a stray value never empties a file.
|
|
7
|
+
*/
|
|
8
|
+
export function boardSvgExportOptions(params) {
|
|
9
|
+
const given = (params !== null && typeof params === 'object' ? params : {});
|
|
10
|
+
return {
|
|
11
|
+
framework: given.framework !== false,
|
|
12
|
+
shapes: given.shapes !== false,
|
|
13
|
+
texts: given.texts !== false,
|
|
14
|
+
};
|
|
15
|
+
}
|
|
16
|
+
/** `'wardley:component'` → `'wardley'`; nothing for a missing or empty role. */
|
|
17
|
+
const namespaceOf = (role) => role?.split(':')[0] || undefined;
|
|
18
|
+
/**
|
|
19
|
+
* Which switch an element on `board` answers to.
|
|
20
|
+
*
|
|
21
|
+
* - **Framework elements**: the board itself; anything whose role shares the
|
|
22
|
+
* board's role namespace (`wardley:map` owns `wardley:component`,
|
|
23
|
+
* `wardley:label`, `wardley:dependency`…); the generated legend
|
|
24
|
+
* (`core:legend`, ADR 0026) and every glyph in it; and a ROLE-LESS element
|
|
25
|
+
* grouped with any of those. The last clause is what a framework artefact is
|
|
26
|
+
* made of: an EDGY person and its name, a Wardley market and its three dots,
|
|
27
|
+
* a Core Domain sub-domain and its title are one group in which only one
|
|
28
|
+
* member carries the role.
|
|
29
|
+
* - **Other texts**: any other `text` element — a plain one, or one of ANOTHER
|
|
30
|
+
* framework lying on this board, which is a text like any other here.
|
|
31
|
+
* - **Other shapes and strokes**: everything else — plain shapes, plain
|
|
32
|
+
* connectors, brush and highlighter strokes, mind maps, another framework's
|
|
33
|
+
* shapes, and a plain group (which paints nothing of its own in an export).
|
|
34
|
+
*
|
|
35
|
+
* Read off the namespace rather than a `FrameworkId` on purpose: three DDD
|
|
36
|
+
* frameworks spell their roles `es:`, `core-domain:` and `context-map:`, and
|
|
37
|
+
* the board says which one it speaks. A board with no role (Cynefin, which
|
|
38
|
+
* paints its domains itself) owns itself and nothing else. Edgeless text
|
|
39
|
+
* BLOCKS never reach this function: they carry no role and are always "other
|
|
40
|
+
* texts" ({@link selectBoardSvgParts}).
|
|
41
|
+
*/
|
|
42
|
+
export function boardSvgExportPartOf(board, element, groups) {
|
|
43
|
+
if (element === board)
|
|
44
|
+
return 'framework';
|
|
45
|
+
const own = namespaceOf(board.role);
|
|
46
|
+
const owned = (role) => role === LEGEND_ROLE || (own !== undefined && namespaceOf(role) === own);
|
|
47
|
+
if (owned(element.role))
|
|
48
|
+
return 'framework';
|
|
49
|
+
if (element.role === undefined) {
|
|
50
|
+
const enclosing = element.childElements ? [element, ...groups] : groups;
|
|
51
|
+
const ownedGroup = enclosing.some(group => owned(group.role) ||
|
|
52
|
+
group.childElements?.some(child => owned(child.role)));
|
|
53
|
+
if (ownedGroup)
|
|
54
|
+
return 'framework';
|
|
55
|
+
}
|
|
56
|
+
return element.type === 'text' ? 'texts' : 'shapes';
|
|
57
|
+
}
|
|
58
|
+
/**
|
|
59
|
+
* What the file draws under `options`: the canvas elements, in the paint order
|
|
60
|
+
* they came in, and the edgeless text blocks, which are all "other texts".
|
|
61
|
+
*/
|
|
62
|
+
export function selectBoardSvgParts(board, elements, textBlocks, options, groupsOf) {
|
|
63
|
+
return {
|
|
64
|
+
elements: elements.filter(element => options[boardSvgExportPartOf(board, element, groupsOf(element))]),
|
|
65
|
+
textBlocks: options.texts ? [...textBlocks] : [],
|
|
66
|
+
};
|
|
67
|
+
}
|
|
@@ -1,13 +1,30 @@
|
|
|
1
1
|
import { FrameworkBackgroundElementModel } from '../../../affine-model/index.js';
|
|
2
2
|
import { Bound } from '../../../global/gfx/index.js';
|
|
3
3
|
import type { BlockStdScope } from '../../../std/index.js';
|
|
4
|
-
import { type GfxPrimitiveElementModel } from '../../../std/gfx/index.js';
|
|
4
|
+
import { type GfxBlockElementModel, type GfxPrimitiveElementModel } from '../../../std/gfx/index.js';
|
|
5
|
+
import type { ExtensionType } from '../../../store/index.js';
|
|
6
|
+
import { CanvasRenderer } from '../../renderer/canvas-renderer.js';
|
|
7
|
+
import { type BoardSvgExportOptions } from './parts.js';
|
|
5
8
|
export interface BoardSvgExport {
|
|
6
9
|
/** A standalone SVG document. */
|
|
7
10
|
svg: string;
|
|
8
11
|
/** The world-space rectangle the document covers. */
|
|
9
12
|
bound: Bound;
|
|
10
13
|
}
|
|
14
|
+
/**
|
|
15
|
+
* How a BLOCK paints itself into the export's 2D context, in model units, the
|
|
16
|
+
* block's top-left at the origin of `matrix`.
|
|
17
|
+
*
|
|
18
|
+
* Blocks are DOM, so the canvas renderer never sees them (ADR 0025,
|
|
19
|
+
* Consequences). The one block the export draws anyway is the edgeless text —
|
|
20
|
+
* what the text tool creates by default — and its painter lives with it, in
|
|
21
|
+
* `@labre/affine-block-edgeless-text`, because the text metrics it needs
|
|
22
|
+
* (`@labre/affine-gfx-text`) sit ABOVE this package. Keyed by flavour; a block
|
|
23
|
+
* with no painter registered is simply not drawn.
|
|
24
|
+
*/
|
|
25
|
+
export type BlockSvgPainter<T extends GfxBlockElementModel = GfxBlockElementModel> = (model: T, ctx: CanvasRenderingContext2D, matrix: DOMMatrix, renderer: CanvasRenderer) => void;
|
|
26
|
+
export declare const BlockSvgPainterIdentifier: import("../../../global/di/types.js").ServiceIdentifier<BlockSvgPainter<GfxBlockElementModel<import("../../../std/gfx/index.js").GfxCompatibleProps>>> & (<U extends BlockSvgPainter<GfxBlockElementModel<import("../../../std/gfx/index.js").GfxCompatibleProps>> = BlockSvgPainter<GfxBlockElementModel<import("../../../std/gfx/index.js").GfxCompatibleProps>>>(variant: import("../../../global/di/types.js").ServiceVariant) => import("../../../global/di/types.js").ServiceIdentifier<U>);
|
|
27
|
+
export declare function BlockSvgPainterExtension<T extends GfxBlockElementModel>(flavour: string, painter: BlockSvgPainter<T>): ExtensionType;
|
|
11
28
|
/**
|
|
12
29
|
* The canvas elements that make up `board`'s picture, in paint order.
|
|
13
30
|
*
|
|
@@ -28,14 +45,54 @@ export interface BoardSvgExport {
|
|
|
28
45
|
*/
|
|
29
46
|
export declare function selectBoardElements<T extends GfxPrimitiveElementModel>(board: FrameworkBackgroundElementModel, candidates: readonly T[]): (FrameworkBackgroundElementModel | T)[];
|
|
30
47
|
/**
|
|
31
|
-
* The
|
|
32
|
-
*
|
|
33
|
-
*
|
|
48
|
+
* The frame, widened to the union of what is painted: a Wardley label
|
|
49
|
+
* overhanging the right edge, or a connector ending just outside, is part of
|
|
50
|
+
* the picture and must not be cut off. The frame is the board's — or, with
|
|
51
|
+
* "Framework elements" switched off, the first thing still drawn.
|
|
34
52
|
*/
|
|
35
|
-
export declare function exportBoundOf(
|
|
53
|
+
export declare function exportBoundOf(frame: {
|
|
54
|
+
readonly xywh: string;
|
|
55
|
+
}, elements: readonly {
|
|
56
|
+
readonly xywh: string;
|
|
57
|
+
}[]): Bound;
|
|
36
58
|
/**
|
|
37
59
|
* The selected board and everything painted within its frame, as an SVG
|
|
38
60
|
* document — a true vector export, produced by replaying the very element
|
|
39
61
|
* renderers the canvas uses into an SVG-emitting 2D context.
|
|
62
|
+
*
|
|
63
|
+
* `options` says which parts are drawn (`parts.ts`). `null` when they leave
|
|
64
|
+
* nothing to draw: an empty file is not a picture of anything.
|
|
65
|
+
*
|
|
66
|
+
* Without `options` every part is drawn, the board among them, so the 0.43
|
|
67
|
+
* call shape `renderBoardSvg(std, board).svg` keeps its non-null return
|
|
68
|
+
* (`render-board-svg-signature.unit.spec.ts`). Only the overload that takes
|
|
69
|
+
* options can answer `null`.
|
|
40
70
|
*/
|
|
41
71
|
export declare function renderBoardSvg(std: BlockStdScope, board: FrameworkBackgroundElementModel): BoardSvgExport;
|
|
72
|
+
export declare function renderBoardSvg(std: BlockStdScope, board: FrameworkBackgroundElementModel, options: Readonly<BoardSvgExportOptions>): BoardSvgExport | null;
|
|
73
|
+
/**
|
|
74
|
+
* What an element's group says about it in the file (ADR 0032 §6): its id, its
|
|
75
|
+
* type, its role, its stored bound in the FILE's coordinates, the two ends of
|
|
76
|
+
* a connector and the group it belongs to — base-class fields only, so every
|
|
77
|
+
* board's SVG carries them and no framework is named here.
|
|
78
|
+
*
|
|
79
|
+
* Ids and vocabulary, never prose: no `pivotDocId` (its contract forbids an
|
|
80
|
+
* exporter to read it), no `interchange`, no tag, no link, no text — a name is
|
|
81
|
+
* read back from the `<text>` the renderer already drew.
|
|
82
|
+
*/
|
|
83
|
+
export declare function boardSvgMarkers(element: {
|
|
84
|
+
id: string;
|
|
85
|
+
xywh: string;
|
|
86
|
+
type?: string;
|
|
87
|
+
flavour?: string;
|
|
88
|
+
role?: string;
|
|
89
|
+
group?: {
|
|
90
|
+
id: string;
|
|
91
|
+
} | null;
|
|
92
|
+
source?: {
|
|
93
|
+
id?: string;
|
|
94
|
+
} | null;
|
|
95
|
+
target?: {
|
|
96
|
+
id?: string;
|
|
97
|
+
} | null;
|
|
98
|
+
}, bound: Bound): Record<string, string>;
|