roosterjs-content-model-plugins 9.46.0 → 9.48.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/lib/imageEdit/ImageEditPlugin.js +1 -1
- package/lib/imageEdit/ImageEditPlugin.js.map +1 -1
- package/lib/imageEdit/types/ImageEditOptions.d.ts +18 -0
- package/lib/imageEdit/types/ImageEditOptions.js.map +1 -1
- package/lib/imageEdit/utils/canRegenerateImage.d.ts +2 -1
- package/lib/imageEdit/utils/canRegenerateImage.js +10 -1
- package/lib/imageEdit/utils/canRegenerateImage.js.map +1 -1
- package/lib/imageEdit/utils/createImageWrapper.js +4 -3
- package/lib/imageEdit/utils/createImageWrapper.js.map +1 -1
- package/lib/paste/WacComponents/processPastedContentWacComponents.js +2 -3
- package/lib/paste/WacComponents/processPastedContentWacComponents.js.map +1 -1
- package/lib/paste/WordDesktop/processPastedContentFromWordDesktop.js +2 -0
- package/lib/paste/WordDesktop/processPastedContentFromWordDesktop.js.map +1 -1
- package/lib/paste/parsers/adjustWordListMarginParser.d.ts +9 -0
- package/lib/paste/parsers/adjustWordListMarginParser.js +26 -0
- package/lib/paste/parsers/adjustWordListMarginParser.js.map +1 -0
- package/lib/tableEdit/editors/features/TableMover.js +2 -3
- package/lib/tableEdit/editors/features/TableMover.js.map +1 -1
- package/lib/touch/TouchPlugin.js +3 -3
- package/lib/touch/TouchPlugin.js.map +1 -1
- package/lib-amd/imageEdit/ImageEditPlugin.js +1 -1
- package/lib-amd/imageEdit/ImageEditPlugin.js.map +1 -1
- package/lib-amd/imageEdit/types/ImageEditOptions.d.ts +18 -0
- package/lib-amd/imageEdit/types/ImageEditOptions.js.map +1 -1
- package/lib-amd/imageEdit/utils/canRegenerateImage.d.ts +2 -1
- package/lib-amd/imageEdit/utils/canRegenerateImage.js +10 -1
- package/lib-amd/imageEdit/utils/canRegenerateImage.js.map +1 -1
- package/lib-amd/imageEdit/utils/createImageWrapper.js +4 -3
- package/lib-amd/imageEdit/utils/createImageWrapper.js.map +1 -1
- package/lib-amd/paste/WacComponents/processPastedContentWacComponents.js +2 -3
- package/lib-amd/paste/WacComponents/processPastedContentWacComponents.js.map +1 -1
- package/lib-amd/paste/WordDesktop/processPastedContentFromWordDesktop.js +2 -1
- package/lib-amd/paste/WordDesktop/processPastedContentFromWordDesktop.js.map +1 -1
- package/lib-amd/paste/parsers/adjustWordListMarginParser.d.ts +9 -0
- package/lib-amd/paste/parsers/adjustWordListMarginParser.js +27 -0
- package/lib-amd/paste/parsers/adjustWordListMarginParser.js.map +1 -0
- package/lib-amd/tableEdit/editors/features/TableMover.js +3 -3
- package/lib-amd/tableEdit/editors/features/TableMover.js.map +1 -1
- package/lib-amd/touch/TouchPlugin.js +3 -3
- package/lib-amd/touch/TouchPlugin.js.map +1 -1
- package/lib-mjs/imageEdit/ImageEditPlugin.js +1 -1
- package/lib-mjs/imageEdit/ImageEditPlugin.js.map +1 -1
- package/lib-mjs/imageEdit/types/ImageEditOptions.d.ts +18 -0
- package/lib-mjs/imageEdit/types/ImageEditOptions.js.map +1 -1
- package/lib-mjs/imageEdit/utils/canRegenerateImage.d.ts +2 -1
- package/lib-mjs/imageEdit/utils/canRegenerateImage.js +10 -1
- package/lib-mjs/imageEdit/utils/canRegenerateImage.js.map +1 -1
- package/lib-mjs/imageEdit/utils/createImageWrapper.js +4 -3
- package/lib-mjs/imageEdit/utils/createImageWrapper.js.map +1 -1
- package/lib-mjs/paste/WacComponents/processPastedContentWacComponents.js +2 -3
- package/lib-mjs/paste/WacComponents/processPastedContentWacComponents.js.map +1 -1
- package/lib-mjs/paste/WordDesktop/processPastedContentFromWordDesktop.js +2 -0
- package/lib-mjs/paste/WordDesktop/processPastedContentFromWordDesktop.js.map +1 -1
- package/lib-mjs/paste/parsers/adjustWordListMarginParser.d.ts +9 -0
- package/lib-mjs/paste/parsers/adjustWordListMarginParser.js +22 -0
- package/lib-mjs/paste/parsers/adjustWordListMarginParser.js.map +1 -0
- package/lib-mjs/tableEdit/editors/features/TableMover.js +3 -4
- package/lib-mjs/tableEdit/editors/features/TableMover.js.map +1 -1
- package/lib-mjs/touch/TouchPlugin.js +3 -3
- package/lib-mjs/touch/TouchPlugin.js.map +1 -1
- package/package.json +5 -5
- package/lib/utils/getNodePositionFromEvent.d.ts +0 -5
- package/lib/utils/getNodePositionFromEvent.js +0 -34
- package/lib/utils/getNodePositionFromEvent.js.map +0 -1
- package/lib-amd/utils/getNodePositionFromEvent.d.ts +0 -5
- package/lib-amd/utils/getNodePositionFromEvent.js +0 -36
- package/lib-amd/utils/getNodePositionFromEvent.js.map +0 -1
- package/lib-mjs/utils/getNodePositionFromEvent.d.ts +0 -5
- package/lib-mjs/utils/getNodePositionFromEvent.js +0 -30
- package/lib-mjs/utils/getNodePositionFromEvent.js.map +0 -1
|
@@ -7,12 +7,21 @@ define(["require", "exports"], function (require, exports) {
|
|
|
7
7
|
* Check if we can regenerate edited image from the source image.
|
|
8
8
|
* An image can't regenerate result when there is CORS issue of the source content.
|
|
9
9
|
* @param img The image element to test
|
|
10
|
+
* @param resolveImageSource Optional callback to resolve an image `src` into a canvas-safe URL (e.g., a data URL).
|
|
10
11
|
* @returns True when we can regenerate the edited image, otherwise false
|
|
11
12
|
*/
|
|
12
|
-
function canRegenerateImage(img) {
|
|
13
|
+
function canRegenerateImage(img, resolveImageSource) {
|
|
13
14
|
if (!img) {
|
|
14
15
|
return false;
|
|
15
16
|
}
|
|
17
|
+
// If a resolveImageSource callback is provided, the image source should be resolved to a
|
|
18
|
+
// canvas-compatible URL when editing starts, so we can assume the image can be regenerated.
|
|
19
|
+
if (resolveImageSource && img.src) {
|
|
20
|
+
var resolved = resolveImageSource(img.src);
|
|
21
|
+
if (resolved && resolved !== img.src) {
|
|
22
|
+
return true;
|
|
23
|
+
}
|
|
24
|
+
}
|
|
16
25
|
try {
|
|
17
26
|
var canvas = img.ownerDocument.createElement('canvas');
|
|
18
27
|
canvas.width = 10;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"canRegenerateImage.js","sourceRoot":"","sources":["../../../../../packages/roosterjs-content-model-plugins/lib/imageEdit/utils/canRegenerateImage.ts"],"names":[],"mappings":";;;;IAAA
|
|
1
|
+
{"version":3,"file":"canRegenerateImage.js","sourceRoot":"","sources":["../../../../../packages/roosterjs-content-model-plugins/lib/imageEdit/utils/canRegenerateImage.ts"],"names":[],"mappings":";;;;IAAA;;;;;;;OAOG;IACH,SAAgB,kBAAkB,CAC9B,GAA4B,EAC5B,kBAAwD;QAExD,IAAI,CAAC,GAAG,EAAE;YACN,OAAO,KAAK,CAAC;SAChB;QAED,yFAAyF;QACzF,4FAA4F;QAC5F,IAAI,kBAAkB,IAAI,GAAG,CAAC,GAAG,EAAE;YAC/B,IAAM,QAAQ,GAAG,kBAAkB,CAAC,GAAG,CAAC,GAAG,CAAC,CAAC;YAC7C,IAAI,QAAQ,IAAI,QAAQ,KAAK,GAAG,CAAC,GAAG,EAAE;gBAClC,OAAO,IAAI,CAAC;aACf;SACJ;QAED,IAAI;YACA,IAAM,MAAM,GAAG,GAAG,CAAC,aAAa,CAAC,aAAa,CAAC,QAAQ,CAAC,CAAC;YACzD,MAAM,CAAC,KAAK,GAAG,EAAE,CAAC;YAClB,MAAM,CAAC,MAAM,GAAG,EAAE,CAAC;YACnB,IAAM,OAAO,GAAG,MAAM,CAAC,UAAU,CAAC,IAAI,CAAC,CAAC;YACxC,IAAI,OAAO,EAAE;gBACT,OAAO,CAAC,SAAS,CAAC,GAAG,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC;gBAC7B,OAAO,CAAC,YAAY,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC;gBACjC,OAAO,IAAI,CAAC;aACf;YAED,OAAO,KAAK,CAAC;SAChB;QAAC,WAAM;YACJ,OAAO,KAAK,CAAC;SAChB;IACL,CAAC;IAhCD,gDAgCC","sourcesContent":["/**\n * @internal\n * Check if we can regenerate edited image from the source image.\n * An image can't regenerate result when there is CORS issue of the source content.\n * @param img The image element to test\n * @param resolveImageSource Optional callback to resolve an image `src` into a canvas-safe URL (e.g., a data URL).\n * @returns True when we can regenerate the edited image, otherwise false\n */\nexport function canRegenerateImage(\n img: HTMLImageElement | null,\n resolveImageSource?: (src: string) => string | undefined\n): boolean {\n if (!img) {\n return false;\n }\n\n // If a resolveImageSource callback is provided, the image source should be resolved to a\n // canvas-compatible URL when editing starts, so we can assume the image can be regenerated.\n if (resolveImageSource && img.src) {\n const resolved = resolveImageSource(img.src);\n if (resolved && resolved !== img.src) {\n return true;\n }\n }\n\n try {\n const canvas = img.ownerDocument.createElement('canvas');\n canvas.width = 10;\n canvas.height = 10;\n const context = canvas.getContext('2d');\n if (context) {\n context.drawImage(img, 0, 0);\n context.getImageData(0, 0, 1, 1);\n return true;\n }\n\n return false;\n } catch {\n return false;\n }\n}\n"]}
|
|
@@ -7,7 +7,7 @@ define(["require", "exports", "../Cropper/createImageCropper", "../Resizer/creat
|
|
|
7
7
|
* @internal
|
|
8
8
|
*/
|
|
9
9
|
function createImageWrapper(editor, image, options, editInfo, htmlOptions, operation) {
|
|
10
|
-
var imageClone = cloneImage(image, editInfo);
|
|
10
|
+
var imageClone = cloneImage(image, editInfo, options.resolveImageSource);
|
|
11
11
|
var doc = editor.getDocument();
|
|
12
12
|
var rotators = [];
|
|
13
13
|
if (!options.disableRotate && operation.indexOf('rotate') > -1) {
|
|
@@ -73,11 +73,12 @@ define(["require", "exports", "../Cropper/createImageCropper", "../Resizer/creat
|
|
|
73
73
|
resizeBorder.setAttribute("style", "position:absolute;left:0;right:0;top:0;bottom:0;border:solid 2px " + borderColor + ";pointer-events:none;");
|
|
74
74
|
return resizeBorder;
|
|
75
75
|
};
|
|
76
|
-
var cloneImage = function (image, editInfo) {
|
|
76
|
+
var cloneImage = function (image, editInfo, resolveImageSource) {
|
|
77
|
+
var _a;
|
|
77
78
|
var imageClone = image.cloneNode(true);
|
|
78
79
|
imageClone.style.removeProperty('transform');
|
|
79
80
|
if (editInfo.src) {
|
|
80
|
-
imageClone.src = editInfo.src;
|
|
81
|
+
imageClone.src = (_a = resolveImageSource === null || resolveImageSource === void 0 ? void 0 : resolveImageSource(editInfo.src)) !== null && _a !== void 0 ? _a : editInfo.src;
|
|
81
82
|
imageClone.removeAttribute('id');
|
|
82
83
|
imageClone.style.removeProperty('max-width');
|
|
83
84
|
imageClone.style.removeProperty('max-height');
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"createImageWrapper.js","sourceRoot":"","sources":["../../../../../packages/roosterjs-content-model-plugins/lib/imageEdit/utils/createImageWrapper.ts"],"names":[],"mappings":";;;;IAaA,IAAM,sBAAsB,GAAG,qBAAqB,CAAC;IAcrD;;OAEG;IACH,SAAgB,kBAAkB,CAC9B,MAAe,EACf,KAAuB,EACvB,OAAyB,EACzB,QAA6B,EAC7B,WAA6B,EAC7B,SAA+B;QAE/B,IAAM,UAAU,GAAG,UAAU,CAAC,KAAK,EAAE,QAAQ,CAAC,CAAC;
|
|
1
|
+
{"version":3,"file":"createImageWrapper.js","sourceRoot":"","sources":["../../../../../packages/roosterjs-content-model-plugins/lib/imageEdit/utils/createImageWrapper.ts"],"names":[],"mappings":"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","sourcesContent":["import { createImageCropper } from '../Cropper/createImageCropper';\nimport { createImageResizer } from '../Resizer/createImageResizer';\nimport { createImageRotator } from '../Rotator/createImageRotator';\nimport { wrap } from 'roosterjs-content-model-dom';\n\nimport type {\n IEditor,\n ImageEditOperation,\n ImageMetadataFormat,\n} from 'roosterjs-content-model-types';\nimport type { ImageEditOptions } from '../types/ImageEditOptions';\nimport type { ImageHtmlOptions } from '../types/ImageHtmlOptions';\n\nconst IMAGE_EDIT_SHADOW_ROOT = 'ImageEditShadowRoot';\n\n/**\n * @internal\n */\nexport interface WrapperElements {\n wrapper: HTMLSpanElement;\n shadowSpan: HTMLElement;\n imageClone: HTMLImageElement;\n resizers: HTMLDivElement[];\n rotators: HTMLDivElement[];\n croppers: HTMLDivElement[];\n}\n\n/**\n * @internal\n */\nexport function createImageWrapper(\n editor: IEditor,\n image: HTMLImageElement,\n options: ImageEditOptions,\n editInfo: ImageMetadataFormat,\n htmlOptions: ImageHtmlOptions,\n operation: ImageEditOperation[]\n): WrapperElements {\n const imageClone = cloneImage(image, editInfo, options.resolveImageSource);\n const doc = editor.getDocument();\n\n let rotators: HTMLDivElement[] = [];\n if (!options.disableRotate && operation.indexOf('rotate') > -1) {\n rotators = createImageRotator(doc, htmlOptions);\n }\n let resizers: HTMLDivElement[] = [];\n if (operation.indexOf('resize') > -1) {\n resizers = createImageResizer(doc, !!options.disableSideResize);\n }\n\n let croppers: HTMLDivElement[] = [];\n if (operation.indexOf('crop') > -1) {\n croppers = createImageCropper(doc);\n }\n\n const wrapper = createWrapper(\n editor,\n imageClone,\n options,\n editInfo,\n resizers,\n rotators,\n croppers\n );\n const imageSpan = wrap(doc, image, 'span');\n const shadowSpan = createShadowSpan(wrapper, imageSpan);\n return { wrapper, shadowSpan, imageClone, resizers, rotators, croppers };\n}\n\nconst createShadowSpan = (wrapper: HTMLElement, imageSpan: HTMLSpanElement) => {\n const shadowRoot = imageSpan.attachShadow({\n mode: 'open',\n });\n imageSpan.id = IMAGE_EDIT_SHADOW_ROOT;\n shadowRoot.appendChild(wrapper);\n return imageSpan;\n};\n\nconst createWrapper = (\n editor: IEditor,\n image: HTMLImageElement,\n options: ImageEditOptions,\n editInfo: ImageMetadataFormat,\n resizers?: HTMLDivElement[],\n rotators?: HTMLDivElement[],\n cropper?: HTMLDivElement[]\n) => {\n const doc = editor.getDocument();\n const wrapper = doc.createElement('span');\n const imageBox = doc.createElement('div');\n\n imageBox.setAttribute(\n `style`,\n `position:relative;width:100%;height:100%;overflow:hidden;transform:scale(1);`\n );\n imageBox.appendChild(image);\n wrapper.setAttribute(\n 'style',\n `font-size: 24px; margin: 0px; transform: rotate(${editInfo.angleRad ?? 0}rad);`\n );\n wrapper.style.display = editor.getEnvironment().isSafari\n ? '-webkit-inline-flex'\n : 'inline-flex';\n\n const border = createBorder(editor, options.borderColor);\n wrapper.appendChild(imageBox);\n wrapper.appendChild(border);\n wrapper.style.userSelect = 'none';\n\n if (resizers && resizers?.length > 0) {\n resizers.forEach(resizer => {\n wrapper.appendChild(resizer);\n });\n }\n if (rotators && rotators.length > 0) {\n rotators.forEach(r => {\n wrapper.appendChild(r);\n });\n }\n if (cropper && cropper.length > 0) {\n cropper.forEach(c => {\n wrapper.appendChild(c);\n });\n }\n\n return wrapper;\n};\n\nconst createBorder = (editor: IEditor, borderColor?: string) => {\n const doc = editor.getDocument();\n const resizeBorder = doc.createElement('div');\n resizeBorder.setAttribute(\n `style`,\n `position:absolute;left:0;right:0;top:0;bottom:0;border:solid 2px ${borderColor};pointer-events:none;`\n );\n return resizeBorder;\n};\n\nconst cloneImage = (\n image: HTMLImageElement,\n editInfo: ImageMetadataFormat,\n resolveImageSource?: (src: string) => string | undefined\n) => {\n const imageClone = image.cloneNode(true) as HTMLImageElement;\n imageClone.style.removeProperty('transform');\n if (editInfo.src) {\n imageClone.src = resolveImageSource?.(editInfo.src) ?? editInfo.src;\n imageClone.removeAttribute('id');\n imageClone.style.removeProperty('max-width');\n imageClone.style.removeProperty('max-height');\n imageClone.style.width = editInfo.widthPx + 'px';\n imageClone.style.height = editInfo.heightPx + 'px';\n }\n return imageClone;\n};\n"]}
|
|
@@ -6,6 +6,7 @@ define(["require", "exports", "tslib", "../utils/addParser", "roosterjs-content-
|
|
|
6
6
|
var LIST_ELEMENT_SELECTOR = LIST_ELEMENT_TAGS.join(',');
|
|
7
7
|
var END_OF_PARAGRAPH = 'EOP';
|
|
8
8
|
var SELECTED_CLASS = 'Selected';
|
|
9
|
+
var BASE_PADDING_WAC_LISTS = '1em';
|
|
9
10
|
/**
|
|
10
11
|
* Wac components do not use sub and super tags, instead only add vertical align to a span.
|
|
11
12
|
* This parser normalize the content for content model
|
|
@@ -103,15 +104,13 @@ define(["require", "exports", "tslib", "../utils/addParser", "roosterjs-content-
|
|
|
103
104
|
if (element.style.display === 'block') {
|
|
104
105
|
format.displayForDummyItem = undefined;
|
|
105
106
|
}
|
|
106
|
-
format.marginLeft = undefined;
|
|
107
|
-
format.marginRight = undefined;
|
|
108
107
|
};
|
|
109
108
|
/**
|
|
110
109
|
* Wac usually adds padding to lists which is unwanted so remove it.
|
|
111
110
|
*/
|
|
112
111
|
var wacListLevelParser = function (format) {
|
|
113
112
|
format.marginLeft = undefined;
|
|
114
|
-
format.paddingLeft =
|
|
113
|
+
format.paddingLeft = BASE_PADDING_WAC_LISTS;
|
|
115
114
|
};
|
|
116
115
|
/**
|
|
117
116
|
* This function returns whether we need to clear the list format.
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"processPastedContentWacComponents.js","sourceRoot":"","sources":["../../../../../packages/roosterjs-content-model-plugins/lib/paste/WacComponents/processPastedContentWacComponents.ts"],"names":[],"mappings":"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","sourcesContent":["import { addParser } from '../utils/addParser';\nimport { createListLevel, parseFormat } from 'roosterjs-content-model-dom';\nimport { setProcessor } from '../utils/setProcessor';\nimport {\n COMMENT_HIGHLIGHT_CLASS,\n COMMENT_HIGHLIGHT_CLICKED_CLASS,\n LIST_CONTAINER_ELEMENT_CLASS_NAME,\n REMOVE_MARGIN_ELEMENTS,\n TEMP_ELEMENTS_CLASSES,\n} from './constants';\nimport type {\n BeforePasteEvent,\n ContentModelBlockFormat,\n ContentModelBlockGroup,\n ContentModelListItemLevelFormat,\n ContentModelListLevel,\n ContentModelSegmentFormat,\n DomToModelContext,\n DomToModelListFormat,\n ElementProcessor,\n FormatParser,\n} from 'roosterjs-content-model-types';\n\nconst LIST_ELEMENT_TAGS = ['UL', 'OL', 'LI'];\nconst LIST_ELEMENT_SELECTOR = LIST_ELEMENT_TAGS.join(',');\nconst END_OF_PARAGRAPH = 'EOP';\nconst SELECTED_CLASS = 'Selected';\n\ninterface WacContext extends DomToModelListFormat {\n /**\n * Current list levels\n */\n currentListLevels?: ContentModelListLevel[];\n /**\n * Array to keep the start of the lists and determine if the start override should be set.\n */\n listItemThread?: number[];\n}\n\n/**\n * Wac components do not use sub and super tags, instead only add vertical align to a span.\n * This parser normalize the content for content model\n */\nconst wacSubSuperParser: FormatParser<ContentModelSegmentFormat> = (\n format: ContentModelSegmentFormat,\n element: HTMLElement\n): void => {\n const verticalAlign = element.style.verticalAlign;\n if (verticalAlign === 'super') {\n format.superOrSubScriptSequence = 'super';\n }\n if (verticalAlign === 'sub') {\n format.superOrSubScriptSequence = 'sub';\n }\n};\n\n/**\n * This processor does:\n * 1) Remove the display and margin of the element.\n * 2) When an element should be ignored but should handle the child elements call the default child processor.\n * 3) Removes the End of Paragraph element to avoid empty lines, we should only remove this if the previous element of the EOP is an EmptyTextRun\n * 4) Finally call the default processor.\n * @returns\n */\nconst wacElementProcessor: ElementProcessor<HTMLElement> = (\n group: ContentModelBlockGroup,\n element: HTMLElement,\n context: DomToModelContext\n): void => {\n const elementTag = element.tagName;\n\n if (element.matches(REMOVE_MARGIN_ELEMENTS)) {\n element.style.removeProperty('display');\n element.style.removeProperty('margin');\n }\n\n if (element.classList.contains(LIST_CONTAINER_ELEMENT_CLASS_NAME)) {\n context.elementProcessors.child(group, element, context);\n return;\n }\n\n if (\n TEMP_ELEMENTS_CLASSES.some(className => element.classList.contains(className)) ||\n // This is needed to remove some temporary End of paragraph elements that WAC sometimes preserves\n (element.classList.contains(SELECTED_CLASS) && element.classList.contains(END_OF_PARAGRAPH))\n ) {\n return;\n } else if (shouldClearListContext(elementTag, element, context)) {\n const { listFormat } = context;\n listFormat.levels = [];\n listFormat.listParent = undefined;\n }\n\n context.defaultElementProcessors.element(group, element, context);\n};\n\n/**\n * This processor calls the default list processor and then sets the correct list level and list bullet.\n */\nconst wacLiElementProcessor: ElementProcessor<HTMLLIElement> = (\n group: ContentModelBlockGroup,\n element: HTMLLIElement,\n context: DomToModelContext\n): void => {\n const level = parseInt(element.getAttribute('data-aria-level') ?? '');\n const listFormat = context.listFormat as WacContext;\n const listType =\n listFormat.levels[context.listFormat.levels.length - 1]?.listType ||\n (element.closest('ol,ul')?.tagName.toUpperCase() as 'UL' | 'OL');\n const newLevel: ContentModelListLevel = createListLevel(listType, context.blockFormat);\n parseFormat(element, context.formatParsers.listLevelThread, newLevel.format, context);\n parseFormat(element, context.formatParsers.listLevel, newLevel.format, context);\n context.listFormat.levels = listFormat.currentListLevels || context.listFormat.levels;\n\n if (level > 0) {\n if (level > context.listFormat.levels.length) {\n while (level != context.listFormat.levels.length) {\n context.listFormat.levels.push(newLevel);\n }\n } else {\n context.listFormat.levels.splice(level, context.listFormat.levels.length - 1);\n context.listFormat.levels[level - 1] = newLevel;\n }\n }\n\n context.defaultElementProcessors.li?.(group, element, context);\n\n const listParent = listFormat.listParent;\n if (listParent) {\n const lastblock = listParent.blocks[listParent.blocks.length - 1];\n if (lastblock.blockType == 'BlockGroup' && lastblock.blockGroupType == 'ListItem') {\n const currentLevel = lastblock.levels[lastblock.levels.length - 1];\n updateStartOverride(currentLevel, element, context);\n }\n }\n\n const newLevels: ContentModelListLevel[] = [];\n listFormat.levels.forEach(v => {\n const newValue: ContentModelListLevel = {\n dataset: { ...v.dataset },\n format: { ...v.format },\n listType: v.listType,\n };\n newLevels.push(newValue);\n });\n listFormat.currentListLevels = newLevels;\n listFormat.levels = [];\n};\n\n/**\n * This parsers does:\n * 1) Sets the display for dummy item to undefined when the current style is block.\n * 2) Removes the Margin Left\n */\nconst wacListItemParser: FormatParser<ContentModelListItemLevelFormat> = (\n format: ContentModelListItemLevelFormat,\n element: HTMLElement\n): void => {\n if (element.style.display === 'block') {\n format.displayForDummyItem = undefined;\n }\n\n format.marginLeft = undefined;\n format.marginRight = undefined;\n};\n\n/**\n * Wac usually adds padding to lists which is unwanted so remove it.\n */\nconst wacListLevelParser: FormatParser<ContentModelListItemLevelFormat> = (\n format: ContentModelListItemLevelFormat\n): void => {\n format.marginLeft = undefined;\n format.paddingLeft = undefined;\n};\n\n/**\n * This function returns whether we need to clear the list format.\n * Word Online wraps lists inside divs to have this structure:\n *\n * <div class='ListContainerWrapper'>\n * <ol>...</ol>\n * </div>\n * <div>\n * <p>...</p>\n * <div>\n * <div class='ListContainerWrapper'>\n * <ol>...</ol>\n * </div>\n *\n * So if a elements is not contained inside of a list we should clear the list context to prevent normal text to be\n * transformed into list\n * For the above scenario, if we do not clear the format, the content inside of the second div would be transformed to a list too.\n */\nfunction shouldClearListContext(\n elementTag: string,\n element: HTMLElement,\n context: DomToModelContext\n) {\n return (\n context.listFormat.levels.length > 0 &&\n LIST_ELEMENT_TAGS.every(tag => tag != elementTag) &&\n !element.closest(LIST_ELEMENT_SELECTOR)\n );\n}\n\nconst wacCommentParser: FormatParser<ContentModelSegmentFormat> = (\n format: ContentModelSegmentFormat,\n element: HTMLElement\n): void => {\n if (\n element.className.includes(COMMENT_HIGHLIGHT_CLASS) ||\n element.className.includes(COMMENT_HIGHLIGHT_CLICKED_CLASS)\n ) {\n delete format.backgroundColor;\n }\n};\n/**\n * @internal\n * Convert pasted content from Office Online\n * Once it is known that the document is from WAC\n * We need to remove the display property and margin from all the list item\n * @param ev BeforePasteEvent\n */\nexport function processPastedContentWacComponents(ev: BeforePasteEvent) {\n addParser(ev.domToModelOption, 'segment', wacSubSuperParser);\n addParser(ev.domToModelOption, 'listItemThread', wacListItemParser);\n addParser(ev.domToModelOption, 'listItemElement', wacListItemParser);\n addParser(ev.domToModelOption, 'listLevel', wacListLevelParser);\n addParser(ev.domToModelOption, 'container', wacContainerParser);\n addParser(ev.domToModelOption, 'table', wacContainerParser);\n addParser(ev.domToModelOption, 'segment', wacCommentParser);\n\n setProcessor(ev.domToModelOption, 'element', wacElementProcessor);\n setProcessor(ev.domToModelOption, 'li', wacLiElementProcessor);\n}\n\nconst wacContainerParser: FormatParser<ContentModelBlockFormat> = (\n format: ContentModelBlockFormat,\n element: HTMLElement\n) => {\n if (element.style.marginLeft.startsWith('-')) {\n delete format.marginLeft;\n }\n};\n\nfunction updateStartOverride(\n currentLevel: ContentModelListLevel | undefined,\n element: HTMLLIElement,\n ctx: DomToModelContext\n) {\n if (!currentLevel || currentLevel.listType == 'UL') {\n return;\n }\n\n const list = element.closest('ol');\n const listFormat = ctx.listFormat as WacContext;\n const [start, listLevel] = extractWordListMetadata(list, element);\n\n if (!listFormat.listItemThread) {\n listFormat.listItemThread = [];\n }\n\n const thread: number | undefined = listFormat.listItemThread[listLevel];\n if (thread && start - thread != 1) {\n currentLevel.format.startNumberOverride = start;\n }\n listFormat.listItemThread[listLevel] = start;\n}\nfunction extractWordListMetadata(\n list: HTMLElement | null | undefined,\n item: HTMLElement | null | undefined\n) {\n const itemIndex =\n item && Array.from(list?.querySelectorAll('li') || []).indexOf(item as HTMLLIElement);\n const start =\n parseInt(list?.getAttribute('start') || '1') + (itemIndex && itemIndex > 0 ? itemIndex : 0);\n const listLevel = parseInt(item?.getAttribute('data-aria-level') || '');\n\n return [start, listLevel];\n}\n"]}
|
|
1
|
+
{"version":3,"file":"processPastedContentWacComponents.js","sourceRoot":"","sources":["../../../../../packages/roosterjs-content-model-plugins/lib/paste/WacComponents/processPastedContentWacComponents.ts"],"names":[],"mappings":";;;;IAuBA,IAAM,iBAAiB,GAAG,CAAC,IAAI,EAAE,IAAI,EAAE,IAAI,CAAC,CAAC;IAC7C,IAAM,qBAAqB,GAAG,iBAAiB,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;IAC1D,IAAM,gBAAgB,GAAG,KAAK,CAAC;IAC/B,IAAM,cAAc,GAAG,UAAU,CAAC;IAClC,IAAM,sBAAsB,GAAG,KAAK,CAAC;IAarC;;;OAGG;IACH,IAAM,iBAAiB,GAA4C,UAC/D,MAAiC,EACjC,OAAoB;QAEpB,IAAM,aAAa,GAAG,OAAO,CAAC,KAAK,CAAC,aAAa,CAAC;QAClD,IAAI,aAAa,KAAK,OAAO,EAAE;YAC3B,MAAM,CAAC,wBAAwB,GAAG,OAAO,CAAC;SAC7C;QACD,IAAI,aAAa,KAAK,KAAK,EAAE;YACzB,MAAM,CAAC,wBAAwB,GAAG,KAAK,CAAC;SAC3C;IACL,CAAC,CAAC;IAEF;;;;;;;OAOG;IACH,IAAM,mBAAmB,GAAkC,UACvD,KAA6B,EAC7B,OAAoB,EACpB,OAA0B;QAE1B,IAAM,UAAU,GAAG,OAAO,CAAC,OAAO,CAAC;QAEnC,IAAI,OAAO,CAAC,OAAO,CAAC,kCAAsB,CAAC,EAAE;YACzC,OAAO,CAAC,KAAK,CAAC,cAAc,CAAC,SAAS,CAAC,CAAC;YACxC,OAAO,CAAC,KAAK,CAAC,cAAc,CAAC,QAAQ,CAAC,CAAC;SAC1C;QAED,IAAI,OAAO,CAAC,SAAS,CAAC,QAAQ,CAAC,6CAAiC,CAAC,EAAE;YAC/D,OAAO,CAAC,iBAAiB,CAAC,KAAK,CAAC,KAAK,EAAE,OAAO,EAAE,OAAO,CAAC,CAAC;YACzD,OAAO;SACV;QAED,IACI,iCAAqB,CAAC,IAAI,CAAC,UAAA,SAAS,IAAI,OAAA,OAAO,CAAC,SAAS,CAAC,QAAQ,CAAC,SAAS,CAAC,EAArC,CAAqC,CAAC;YAC9E,iGAAiG;YACjG,CAAC,OAAO,CAAC,SAAS,CAAC,QAAQ,CAAC,cAAc,CAAC,IAAI,OAAO,CAAC,SAAS,CAAC,QAAQ,CAAC,gBAAgB,CAAC,CAAC,EAC9F;YACE,OAAO;SACV;aAAM,IAAI,sBAAsB,CAAC,UAAU,EAAE,OAAO,EAAE,OAAO,CAAC,EAAE;YACrD,IAAA,UAAU,GAAK,OAAO,WAAZ,CAAa;YAC/B,UAAU,CAAC,MAAM,GAAG,EAAE,CAAC;YACvB,UAAU,CAAC,UAAU,GAAG,SAAS,CAAC;SACrC;QAED,OAAO,CAAC,wBAAwB,CAAC,OAAO,CAAC,KAAK,EAAE,OAAO,EAAE,OAAO,CAAC,CAAC;IACtE,CAAC,CAAC;IAEF;;OAEG;IACH,IAAM,qBAAqB,GAAoC,UAC3D,KAA6B,EAC7B,OAAsB,EACtB,OAA0B;;QAE1B,IAAM,KAAK,GAAG,QAAQ,CAAC,MAAA,OAAO,CAAC,YAAY,CAAC,iBAAiB,CAAC,mCAAI,EAAE,CAAC,CAAC;QACtE,IAAM,UAAU,GAAG,OAAO,CAAC,UAAwB,CAAC;QACpD,IAAM,QAAQ,GACV,CAAA,MAAA,UAAU,CAAC,MAAM,CAAC,OAAO,CAAC,UAAU,CAAC,MAAM,CAAC,MAAM,GAAG,CAAC,CAAC,0CAAE,QAAQ;aAChE,MAAA,OAAO,CAAC,OAAO,CAAC,OAAO,CAAC,0CAAE,OAAO,CAAC,WAAW,EAAkB,CAAA,CAAC;QACrE,IAAM,QAAQ,GAA0B,IAAA,6CAAe,EAAC,QAAQ,EAAE,OAAO,CAAC,WAAW,CAAC,CAAC;QACvF,IAAA,yCAAW,EAAC,OAAO,EAAE,OAAO,CAAC,aAAa,CAAC,eAAe,EAAE,QAAQ,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;QACtF,IAAA,yCAAW,EAAC,OAAO,EAAE,OAAO,CAAC,aAAa,CAAC,SAAS,EAAE,QAAQ,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;QAChF,OAAO,CAAC,UAAU,CAAC,MAAM,GAAG,UAAU,CAAC,iBAAiB,IAAI,OAAO,CAAC,UAAU,CAAC,MAAM,CAAC;QAEtF,IAAI,KAAK,GAAG,CAAC,EAAE;YACX,IAAI,KAAK,GAAG,OAAO,CAAC,UAAU,CAAC,MAAM,CAAC,MAAM,EAAE;gBAC1C,OAAO,KAAK,IAAI,OAAO,CAAC,UAAU,CAAC,MAAM,CAAC,MAAM,EAAE;oBAC9C,OAAO,CAAC,UAAU,CAAC,MAAM,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;iBAC5C;aACJ;iBAAM;gBACH,OAAO,CAAC,UAAU,CAAC,MAAM,CAAC,MAAM,CAAC,KAAK,EAAE,OAAO,CAAC,UAAU,CAAC,MAAM,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC;gBAC9E,OAAO,CAAC,UAAU,CAAC,MAAM,CAAC,KAAK,GAAG,CAAC,CAAC,GAAG,QAAQ,CAAC;aACnD;SACJ;QAED,MAAA,MAAA,OAAO,CAAC,wBAAwB,EAAC,EAAE,mDAAG,KAAK,EAAE,OAAO,EAAE,OAAO,CAAC,CAAC;QAE/D,IAAM,UAAU,GAAG,UAAU,CAAC,UAAU,CAAC;QACzC,IAAI,UAAU,EAAE;YACZ,IAAM,SAAS,GAAG,UAAU,CAAC,MAAM,CAAC,UAAU,CAAC,MAAM,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC;YAClE,IAAI,SAAS,CAAC,SAAS,IAAI,YAAY,IAAI,SAAS,CAAC,cAAc,IAAI,UAAU,EAAE;gBAC/E,IAAM,YAAY,GAAG,SAAS,CAAC,MAAM,CAAC,SAAS,CAAC,MAAM,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC;gBACnE,mBAAmB,CAAC,YAAY,EAAE,OAAO,EAAE,OAAO,CAAC,CAAC;aACvD;SACJ;QAED,IAAM,SAAS,GAA4B,EAAE,CAAC;QAC9C,UAAU,CAAC,MAAM,CAAC,OAAO,CAAC,UAAA,CAAC;YACvB,IAAM,QAAQ,GAA0B;gBACpC,OAAO,4BAAO,CAAC,CAAC,OAAO,CAAE;gBACzB,MAAM,4BAAO,CAAC,CAAC,MAAM,CAAE;gBACvB,QAAQ,EAAE,CAAC,CAAC,QAAQ;aACvB,CAAC;YACF,SAAS,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;QAC7B,CAAC,CAAC,CAAC;QACH,UAAU,CAAC,iBAAiB,GAAG,SAAS,CAAC;QACzC,UAAU,CAAC,MAAM,GAAG,EAAE,CAAC;IAC3B,CAAC,CAAC;IAEF;;;;OAIG;IACH,IAAM,iBAAiB,GAAkD,UACrE,MAAuC,EACvC,OAAoB;QAEpB,IAAI,OAAO,CAAC,KAAK,CAAC,OAAO,KAAK,OAAO,EAAE;YACnC,MAAM,CAAC,mBAAmB,GAAG,SAAS,CAAC;SAC1C;IACL,CAAC,CAAC;IAEF;;OAEG;IACH,IAAM,kBAAkB,GAAkD,UACtE,MAAuC;QAEvC,MAAM,CAAC,UAAU,GAAG,SAAS,CAAC;QAC9B,MAAM,CAAC,WAAW,GAAG,sBAAsB,CAAC;IAChD,CAAC,CAAC;IAEF;;;;;;;;;;;;;;;;;OAiBG;IACH,SAAS,sBAAsB,CAC3B,UAAkB,EAClB,OAAoB,EACpB,OAA0B;QAE1B,OAAO,CACH,OAAO,CAAC,UAAU,CAAC,MAAM,CAAC,MAAM,GAAG,CAAC;YACpC,iBAAiB,CAAC,KAAK,CAAC,UAAA,GAAG,IAAI,OAAA,GAAG,IAAI,UAAU,EAAjB,CAAiB,CAAC;YACjD,CAAC,OAAO,CAAC,OAAO,CAAC,qBAAqB,CAAC,CAC1C,CAAC;IACN,CAAC;IAED,IAAM,gBAAgB,GAA4C,UAC9D,MAAiC,EACjC,OAAoB;QAEpB,IACI,OAAO,CAAC,SAAS,CAAC,QAAQ,CAAC,mCAAuB,CAAC;YACnD,OAAO,CAAC,SAAS,CAAC,QAAQ,CAAC,2CAA+B,CAAC,EAC7D;YACE,OAAO,MAAM,CAAC,eAAe,CAAC;SACjC;IACL,CAAC,CAAC;IACF;;;;;;OAMG;IACH,SAAgB,iCAAiC,CAAC,EAAoB;QAClE,IAAA,qBAAS,EAAC,EAAE,CAAC,gBAAgB,EAAE,SAAS,EAAE,iBAAiB,CAAC,CAAC;QAC7D,IAAA,qBAAS,EAAC,EAAE,CAAC,gBAAgB,EAAE,gBAAgB,EAAE,iBAAiB,CAAC,CAAC;QACpE,IAAA,qBAAS,EAAC,EAAE,CAAC,gBAAgB,EAAE,iBAAiB,EAAE,iBAAiB,CAAC,CAAC;QACrE,IAAA,qBAAS,EAAC,EAAE,CAAC,gBAAgB,EAAE,WAAW,EAAE,kBAAkB,CAAC,CAAC;QAChE,IAAA,qBAAS,EAAC,EAAE,CAAC,gBAAgB,EAAE,WAAW,EAAE,kBAAkB,CAAC,CAAC;QAChE,IAAA,qBAAS,EAAC,EAAE,CAAC,gBAAgB,EAAE,OAAO,EAAE,kBAAkB,CAAC,CAAC;QAC5D,IAAA,qBAAS,EAAC,EAAE,CAAC,gBAAgB,EAAE,SAAS,EAAE,gBAAgB,CAAC,CAAC;QAE5D,IAAA,2BAAY,EAAC,EAAE,CAAC,gBAAgB,EAAE,SAAS,EAAE,mBAAmB,CAAC,CAAC;QAClE,IAAA,2BAAY,EAAC,EAAE,CAAC,gBAAgB,EAAE,IAAI,EAAE,qBAAqB,CAAC,CAAC;IACnE,CAAC;IAXD,8EAWC;IAED,IAAM,kBAAkB,GAA0C,UAC9D,MAA+B,EAC/B,OAAoB;QAEpB,IAAI,OAAO,CAAC,KAAK,CAAC,UAAU,CAAC,UAAU,CAAC,GAAG,CAAC,EAAE;YAC1C,OAAO,MAAM,CAAC,UAAU,CAAC;SAC5B;IACL,CAAC,CAAC;IAEF,SAAS,mBAAmB,CACxB,YAA+C,EAC/C,OAAsB,EACtB,GAAsB;QAEtB,IAAI,CAAC,YAAY,IAAI,YAAY,CAAC,QAAQ,IAAI,IAAI,EAAE;YAChD,OAAO;SACV;QAED,IAAM,IAAI,GAAG,OAAO,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC;QACnC,IAAM,UAAU,GAAG,GAAG,CAAC,UAAwB,CAAC;QAC1C,IAAA,KAAA,oBAAqB,uBAAuB,CAAC,IAAI,EAAE,OAAO,CAAC,IAAA,EAA1D,KAAK,QAAA,EAAE,SAAS,QAA0C,CAAC;QAElE,IAAI,CAAC,UAAU,CAAC,cAAc,EAAE;YAC5B,UAAU,CAAC,cAAc,GAAG,EAAE,CAAC;SAClC;QAED,IAAM,MAAM,GAAuB,UAAU,CAAC,cAAc,CAAC,SAAS,CAAC,CAAC;QACxE,IAAI,MAAM,IAAI,KAAK,GAAG,MAAM,IAAI,CAAC,EAAE;YAC/B,YAAY,CAAC,MAAM,CAAC,mBAAmB,GAAG,KAAK,CAAC;SACnD;QACD,UAAU,CAAC,cAAc,CAAC,SAAS,CAAC,GAAG,KAAK,CAAC;IACjD,CAAC;IACD,SAAS,uBAAuB,CAC5B,IAAoC,EACpC,IAAoC;QAEpC,IAAM,SAAS,GACX,IAAI,IAAI,KAAK,CAAC,IAAI,CAAC,CAAA,IAAI,aAAJ,IAAI,uBAAJ,IAAI,CAAE,gBAAgB,CAAC,IAAI,CAAC,KAAI,EAAE,CAAC,CAAC,OAAO,CAAC,IAAqB,CAAC,CAAC;QAC1F,IAAM,KAAK,GACP,QAAQ,CAAC,CAAA,IAAI,aAAJ,IAAI,uBAAJ,IAAI,CAAE,YAAY,CAAC,OAAO,CAAC,KAAI,GAAG,CAAC,GAAG,CAAC,SAAS,IAAI,SAAS,GAAG,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QAChG,IAAM,SAAS,GAAG,QAAQ,CAAC,CAAA,IAAI,aAAJ,IAAI,uBAAJ,IAAI,CAAE,YAAY,CAAC,iBAAiB,CAAC,KAAI,EAAE,CAAC,CAAC;QAExE,OAAO,CAAC,KAAK,EAAE,SAAS,CAAC,CAAC;IAC9B,CAAC","sourcesContent":["import { addParser } from '../utils/addParser';\nimport { createListLevel, parseFormat } from 'roosterjs-content-model-dom';\nimport { setProcessor } from '../utils/setProcessor';\nimport {\n COMMENT_HIGHLIGHT_CLASS,\n COMMENT_HIGHLIGHT_CLICKED_CLASS,\n LIST_CONTAINER_ELEMENT_CLASS_NAME,\n REMOVE_MARGIN_ELEMENTS,\n TEMP_ELEMENTS_CLASSES,\n} from './constants';\nimport type {\n BeforePasteEvent,\n ContentModelBlockFormat,\n ContentModelBlockGroup,\n ContentModelListItemLevelFormat,\n ContentModelListLevel,\n ContentModelSegmentFormat,\n DomToModelContext,\n DomToModelListFormat,\n ElementProcessor,\n FormatParser,\n} from 'roosterjs-content-model-types';\n\nconst LIST_ELEMENT_TAGS = ['UL', 'OL', 'LI'];\nconst LIST_ELEMENT_SELECTOR = LIST_ELEMENT_TAGS.join(',');\nconst END_OF_PARAGRAPH = 'EOP';\nconst SELECTED_CLASS = 'Selected';\nconst BASE_PADDING_WAC_LISTS = '1em';\n\ninterface WacContext extends DomToModelListFormat {\n /**\n * Current list levels\n */\n currentListLevels?: ContentModelListLevel[];\n /**\n * Array to keep the start of the lists and determine if the start override should be set.\n */\n listItemThread?: number[];\n}\n\n/**\n * Wac components do not use sub and super tags, instead only add vertical align to a span.\n * This parser normalize the content for content model\n */\nconst wacSubSuperParser: FormatParser<ContentModelSegmentFormat> = (\n format: ContentModelSegmentFormat,\n element: HTMLElement\n): void => {\n const verticalAlign = element.style.verticalAlign;\n if (verticalAlign === 'super') {\n format.superOrSubScriptSequence = 'super';\n }\n if (verticalAlign === 'sub') {\n format.superOrSubScriptSequence = 'sub';\n }\n};\n\n/**\n * This processor does:\n * 1) Remove the display and margin of the element.\n * 2) When an element should be ignored but should handle the child elements call the default child processor.\n * 3) Removes the End of Paragraph element to avoid empty lines, we should only remove this if the previous element of the EOP is an EmptyTextRun\n * 4) Finally call the default processor.\n * @returns\n */\nconst wacElementProcessor: ElementProcessor<HTMLElement> = (\n group: ContentModelBlockGroup,\n element: HTMLElement,\n context: DomToModelContext\n): void => {\n const elementTag = element.tagName;\n\n if (element.matches(REMOVE_MARGIN_ELEMENTS)) {\n element.style.removeProperty('display');\n element.style.removeProperty('margin');\n }\n\n if (element.classList.contains(LIST_CONTAINER_ELEMENT_CLASS_NAME)) {\n context.elementProcessors.child(group, element, context);\n return;\n }\n\n if (\n TEMP_ELEMENTS_CLASSES.some(className => element.classList.contains(className)) ||\n // This is needed to remove some temporary End of paragraph elements that WAC sometimes preserves\n (element.classList.contains(SELECTED_CLASS) && element.classList.contains(END_OF_PARAGRAPH))\n ) {\n return;\n } else if (shouldClearListContext(elementTag, element, context)) {\n const { listFormat } = context;\n listFormat.levels = [];\n listFormat.listParent = undefined;\n }\n\n context.defaultElementProcessors.element(group, element, context);\n};\n\n/**\n * This processor calls the default list processor and then sets the correct list level and list bullet.\n */\nconst wacLiElementProcessor: ElementProcessor<HTMLLIElement> = (\n group: ContentModelBlockGroup,\n element: HTMLLIElement,\n context: DomToModelContext\n): void => {\n const level = parseInt(element.getAttribute('data-aria-level') ?? '');\n const listFormat = context.listFormat as WacContext;\n const listType =\n listFormat.levels[context.listFormat.levels.length - 1]?.listType ||\n (element.closest('ol,ul')?.tagName.toUpperCase() as 'UL' | 'OL');\n const newLevel: ContentModelListLevel = createListLevel(listType, context.blockFormat);\n parseFormat(element, context.formatParsers.listLevelThread, newLevel.format, context);\n parseFormat(element, context.formatParsers.listLevel, newLevel.format, context);\n context.listFormat.levels = listFormat.currentListLevels || context.listFormat.levels;\n\n if (level > 0) {\n if (level > context.listFormat.levels.length) {\n while (level != context.listFormat.levels.length) {\n context.listFormat.levels.push(newLevel);\n }\n } else {\n context.listFormat.levels.splice(level, context.listFormat.levels.length - 1);\n context.listFormat.levels[level - 1] = newLevel;\n }\n }\n\n context.defaultElementProcessors.li?.(group, element, context);\n\n const listParent = listFormat.listParent;\n if (listParent) {\n const lastblock = listParent.blocks[listParent.blocks.length - 1];\n if (lastblock.blockType == 'BlockGroup' && lastblock.blockGroupType == 'ListItem') {\n const currentLevel = lastblock.levels[lastblock.levels.length - 1];\n updateStartOverride(currentLevel, element, context);\n }\n }\n\n const newLevels: ContentModelListLevel[] = [];\n listFormat.levels.forEach(v => {\n const newValue: ContentModelListLevel = {\n dataset: { ...v.dataset },\n format: { ...v.format },\n listType: v.listType,\n };\n newLevels.push(newValue);\n });\n listFormat.currentListLevels = newLevels;\n listFormat.levels = [];\n};\n\n/**\n * This parsers does:\n * 1) Sets the display for dummy item to undefined when the current style is block.\n * 2) Removes the Margin Left\n */\nconst wacListItemParser: FormatParser<ContentModelListItemLevelFormat> = (\n format: ContentModelListItemLevelFormat,\n element: HTMLElement\n): void => {\n if (element.style.display === 'block') {\n format.displayForDummyItem = undefined;\n }\n};\n\n/**\n * Wac usually adds padding to lists which is unwanted so remove it.\n */\nconst wacListLevelParser: FormatParser<ContentModelListItemLevelFormat> = (\n format: ContentModelListItemLevelFormat\n): void => {\n format.marginLeft = undefined;\n format.paddingLeft = BASE_PADDING_WAC_LISTS;\n};\n\n/**\n * This function returns whether we need to clear the list format.\n * Word Online wraps lists inside divs to have this structure:\n *\n * <div class='ListContainerWrapper'>\n * <ol>...</ol>\n * </div>\n * <div>\n * <p>...</p>\n * <div>\n * <div class='ListContainerWrapper'>\n * <ol>...</ol>\n * </div>\n *\n * So if a elements is not contained inside of a list we should clear the list context to prevent normal text to be\n * transformed into list\n * For the above scenario, if we do not clear the format, the content inside of the second div would be transformed to a list too.\n */\nfunction shouldClearListContext(\n elementTag: string,\n element: HTMLElement,\n context: DomToModelContext\n) {\n return (\n context.listFormat.levels.length > 0 &&\n LIST_ELEMENT_TAGS.every(tag => tag != elementTag) &&\n !element.closest(LIST_ELEMENT_SELECTOR)\n );\n}\n\nconst wacCommentParser: FormatParser<ContentModelSegmentFormat> = (\n format: ContentModelSegmentFormat,\n element: HTMLElement\n): void => {\n if (\n element.className.includes(COMMENT_HIGHLIGHT_CLASS) ||\n element.className.includes(COMMENT_HIGHLIGHT_CLICKED_CLASS)\n ) {\n delete format.backgroundColor;\n }\n};\n/**\n * @internal\n * Convert pasted content from Office Online\n * Once it is known that the document is from WAC\n * We need to remove the display property and margin from all the list item\n * @param ev BeforePasteEvent\n */\nexport function processPastedContentWacComponents(ev: BeforePasteEvent) {\n addParser(ev.domToModelOption, 'segment', wacSubSuperParser);\n addParser(ev.domToModelOption, 'listItemThread', wacListItemParser);\n addParser(ev.domToModelOption, 'listItemElement', wacListItemParser);\n addParser(ev.domToModelOption, 'listLevel', wacListLevelParser);\n addParser(ev.domToModelOption, 'container', wacContainerParser);\n addParser(ev.domToModelOption, 'table', wacContainerParser);\n addParser(ev.domToModelOption, 'segment', wacCommentParser);\n\n setProcessor(ev.domToModelOption, 'element', wacElementProcessor);\n setProcessor(ev.domToModelOption, 'li', wacLiElementProcessor);\n}\n\nconst wacContainerParser: FormatParser<ContentModelBlockFormat> = (\n format: ContentModelBlockFormat,\n element: HTMLElement\n) => {\n if (element.style.marginLeft.startsWith('-')) {\n delete format.marginLeft;\n }\n};\n\nfunction updateStartOverride(\n currentLevel: ContentModelListLevel | undefined,\n element: HTMLLIElement,\n ctx: DomToModelContext\n) {\n if (!currentLevel || currentLevel.listType == 'UL') {\n return;\n }\n\n const list = element.closest('ol');\n const listFormat = ctx.listFormat as WacContext;\n const [start, listLevel] = extractWordListMetadata(list, element);\n\n if (!listFormat.listItemThread) {\n listFormat.listItemThread = [];\n }\n\n const thread: number | undefined = listFormat.listItemThread[listLevel];\n if (thread && start - thread != 1) {\n currentLevel.format.startNumberOverride = start;\n }\n listFormat.listItemThread[listLevel] = start;\n}\nfunction extractWordListMetadata(\n list: HTMLElement | null | undefined,\n item: HTMLElement | null | undefined\n) {\n const itemIndex =\n item && Array.from(list?.querySelectorAll('li') || []).indexOf(item as HTMLLIElement);\n const start =\n parseInt(list?.getAttribute('start') || '1') + (itemIndex && itemIndex > 0 ? itemIndex : 0);\n const listLevel = parseInt(item?.getAttribute('data-aria-level') || '');\n\n return [start, listLevel];\n}\n"]}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
define(["require", "exports", "../utils/addParser", "../parsers/adjustPercentileLineHeightParser", "./getStyleMetadata", "../utils/getStyles", "../parsers/listLevelParser", "./processWordComments", "./processWordLists", "../parsers/removeNegativeTextIndentParser", "../utils/setProcessor", "../parsers/wordContainerParser", "../parsers/wordTableParser"], function (require, exports, addParser_1, adjustPercentileLineHeightParser_1, getStyleMetadata_1, getStyles_1, listLevelParser_1, processWordComments_1, processWordLists_1, removeNegativeTextIndentParser_1, setProcessor_1, wordContainerParser_1, wordTableParser_1) {
|
|
1
|
+
define(["require", "exports", "../utils/addParser", "../parsers/adjustPercentileLineHeightParser", "./getStyleMetadata", "../utils/getStyles", "../parsers/listLevelParser", "./processWordComments", "./processWordLists", "../parsers/adjustWordListMarginParser", "../parsers/removeNegativeTextIndentParser", "../utils/setProcessor", "../parsers/wordContainerParser", "../parsers/wordTableParser"], function (require, exports, addParser_1, adjustPercentileLineHeightParser_1, getStyleMetadata_1, getStyles_1, listLevelParser_1, processWordComments_1, processWordLists_1, adjustWordListMarginParser_1, removeNegativeTextIndentParser_1, setProcessor_1, wordContainerParser_1, wordTableParser_1) {
|
|
2
2
|
"use strict";
|
|
3
3
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
4
4
|
exports.processPastedContentFromWordDesktop = void 0;
|
|
@@ -14,6 +14,7 @@ define(["require", "exports", "../utils/addParser", "../parsers/adjustPercentile
|
|
|
14
14
|
(0, addParser_1.addParser)(domToModelOption, 'block', adjustPercentileLineHeightParser_1.adjustPercentileLineHeight);
|
|
15
15
|
(0, addParser_1.addParser)(domToModelOption, 'block', removeNegativeTextIndentParser_1.removeNegativeTextIndentParser);
|
|
16
16
|
(0, addParser_1.addParser)(domToModelOption, 'listItemElement', removeNegativeTextIndentParser_1.removeNegativeTextIndentParser);
|
|
17
|
+
(0, addParser_1.addParser)(domToModelOption, 'listItemElement', adjustWordListMarginParser_1.adjustWordListMarginParser);
|
|
17
18
|
(0, addParser_1.addParser)(domToModelOption, 'listLevel', listLevelParser_1.listLevelParser);
|
|
18
19
|
(0, addParser_1.addParser)(domToModelOption, 'container', wordContainerParser_1.wordContainerParser);
|
|
19
20
|
(0, addParser_1.addParser)(domToModelOption, 'table', wordTableParser_1.wordTableParser);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"processPastedContentFromWordDesktop.js","sourceRoot":"","sources":["../../../../../packages/roosterjs-content-model-plugins/lib/paste/WordDesktop/processPastedContentFromWordDesktop.ts"],"names":[],"mappings":";;;;
|
|
1
|
+
{"version":3,"file":"processPastedContentFromWordDesktop.js","sourceRoot":"","sources":["../../../../../packages/roosterjs-content-model-plugins/lib/paste/WordDesktop/processPastedContentFromWordDesktop.ts"],"names":[],"mappings":";;;;IAeA;;;;;OAKG;IACH,SAAgB,mCAAmC,CAC/C,gBAAkC,EAClC,UAAkB;QAElB,IAAM,WAAW,GAA8B,IAAA,mCAAgB,EAAC,UAAU,CAAC,CAAC;QAE5E,IAAA,2BAAY,EAAC,gBAAgB,EAAE,SAAS,EAAE,2BAA2B,CAAC,WAAW,CAAC,CAAC,CAAC;QACpF,IAAA,qBAAS,EAAC,gBAAgB,EAAE,OAAO,EAAE,6DAA0B,CAAC,CAAC;QACjE,IAAA,qBAAS,EAAC,gBAAgB,EAAE,OAAO,EAAE,+DAA8B,CAAC,CAAC;QACrE,IAAA,qBAAS,EAAC,gBAAgB,EAAE,iBAAiB,EAAE,+DAA8B,CAAC,CAAC;QAC/E,IAAA,qBAAS,EAAC,gBAAgB,EAAE,iBAAiB,EAAE,uDAA0B,CAAC,CAAC;QAC3E,IAAA,qBAAS,EAAC,gBAAgB,EAAE,WAAW,EAAE,iCAAe,CAAC,CAAC;QAC1D,IAAA,qBAAS,EAAC,gBAAgB,EAAE,WAAW,EAAE,yCAAmB,CAAC,CAAC;QAC9D,IAAA,qBAAS,EAAC,gBAAgB,EAAE,OAAO,EAAE,iCAAe,CAAC,CAAC;IAC1D,CAAC;IAdD,kFAcC;IAED,IAAM,2BAA2B,GAAG,UAChC,WAAsC;QAEtC,OAAO,UAAC,KAAK,EAAE,OAAO,EAAE,OAAO;YAC3B,IAAM,MAAM,GAAG,IAAA,qBAAS,EAAC,OAAO,CAAC,CAAC;YAClC,4FAA4F;YAC5F,IACI,CAAC,CACG,IAAA,kCAAe,EAAC,MAAM,EAAE,KAAK,EAAE,OAAO,EAAE,OAAO,EAAE,WAAW,CAAC;gBAC7D,IAAA,yCAAmB,EAAC,MAAM,EAAE,OAAO,CAAC,CACvC,EACH;gBACE,OAAO,CAAC,wBAAwB,CAAC,OAAO,CAAC,KAAK,EAAE,OAAO,EAAE,OAAO,CAAC,CAAC;aACrE;QACL,CAAC,CAAC;IACN,CAAC,CAAC","sourcesContent":["import { addParser } from '../utils/addParser';\nimport { adjustPercentileLineHeight } from '../parsers/adjustPercentileLineHeightParser';\nimport { getStyleMetadata } from './getStyleMetadata';\nimport { getStyles } from '../utils/getStyles';\nimport { listLevelParser } from '../parsers/listLevelParser';\nimport { processWordComments } from './processWordComments';\nimport { processWordList } from './processWordLists';\nimport { adjustWordListMarginParser } from '../parsers/adjustWordListMarginParser';\nimport { removeNegativeTextIndentParser } from '../parsers/removeNegativeTextIndentParser';\nimport { setProcessor } from '../utils/setProcessor';\nimport { wordContainerParser } from '../parsers/wordContainerParser';\nimport { wordTableParser } from '../parsers/wordTableParser';\nimport type { WordMetadata } from './WordMetadata';\nimport type { DomToModelOption, ElementProcessor } from 'roosterjs-content-model-types';\n\n/**\n * @internal\n * Handles pasted content when the source is Word Desktop.\n * @param domToModelOption Options for DOM to Content Model conversion\n * @param htmlString The HTML string to process\n */\nexport function processPastedContentFromWordDesktop(\n domToModelOption: DomToModelOption,\n htmlString: string\n) {\n const metadataMap: Map<string, WordMetadata> = getStyleMetadata(htmlString);\n\n setProcessor(domToModelOption, 'element', wordDesktopElementProcessor(metadataMap));\n addParser(domToModelOption, 'block', adjustPercentileLineHeight);\n addParser(domToModelOption, 'block', removeNegativeTextIndentParser);\n addParser(domToModelOption, 'listItemElement', removeNegativeTextIndentParser);\n addParser(domToModelOption, 'listItemElement', adjustWordListMarginParser);\n addParser(domToModelOption, 'listLevel', listLevelParser);\n addParser(domToModelOption, 'container', wordContainerParser);\n addParser(domToModelOption, 'table', wordTableParser);\n}\n\nconst wordDesktopElementProcessor = (\n metadataKey: Map<string, WordMetadata>\n): ElementProcessor<HTMLElement> => {\n return (group, element, context) => {\n const styles = getStyles(element);\n // Process Word Lists or Word Commands, otherwise use the default processor on this element.\n if (\n !(\n processWordList(styles, group, element, context, metadataKey) ||\n processWordComments(styles, element)\n )\n ) {\n context.defaultElementProcessors.element(group, element, context);\n }\n };\n};\n"]}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import type { FormatParser, MarginFormat } from 'roosterjs-content-model-types';
|
|
2
|
+
/**
|
|
3
|
+
* @internal
|
|
4
|
+
* Parser that subtracts the default list format (paddingInlineStart: 40px) from
|
|
5
|
+
* the marginLeft of list item elements that have the MsoListParagraph class,
|
|
6
|
+
* since Word adds the full indentation as margin on the paragraph, which
|
|
7
|
+
* duplicates the padding the list element already provides.
|
|
8
|
+
*/
|
|
9
|
+
export declare const adjustWordListMarginParser: FormatParser<MarginFormat>;
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
define(["require", "exports", "roosterjs-content-model-dom"], function (require, exports, roosterjs_content_model_dom_1) {
|
|
2
|
+
"use strict";
|
|
3
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
4
|
+
exports.adjustWordListMarginParser = void 0;
|
|
5
|
+
var MSO_LIST_PARAGRAPH_CLASS = 'MsoListParagraph';
|
|
6
|
+
// Default list padding from the HTML user-agent stylesheet (paddingInlineStart for <ul>/<ol>)
|
|
7
|
+
var DEFAULT_LIST_PADDING_INLINE_START = '40px';
|
|
8
|
+
/**
|
|
9
|
+
* @internal
|
|
10
|
+
* Parser that subtracts the default list format (paddingInlineStart: 40px) from
|
|
11
|
+
* the marginLeft of list item elements that have the MsoListParagraph class,
|
|
12
|
+
* since Word adds the full indentation as margin on the paragraph, which
|
|
13
|
+
* duplicates the padding the list element already provides.
|
|
14
|
+
*/
|
|
15
|
+
var adjustWordListMarginParser = function (format, element) {
|
|
16
|
+
if (element.classList.contains(MSO_LIST_PARAGRAPH_CLASS) && format.marginLeft) {
|
|
17
|
+
var currentPx = (0, roosterjs_content_model_dom_1.parseValueWithUnit)(format.marginLeft, element);
|
|
18
|
+
var defaultPx = (0, roosterjs_content_model_dom_1.parseValueWithUnit)(DEFAULT_LIST_PADDING_INLINE_START);
|
|
19
|
+
var result = currentPx - defaultPx;
|
|
20
|
+
if (result > 0) {
|
|
21
|
+
format.marginLeft = result + "px";
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
};
|
|
25
|
+
exports.adjustWordListMarginParser = adjustWordListMarginParser;
|
|
26
|
+
});
|
|
27
|
+
//# sourceMappingURL=adjustWordListMarginParser.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"adjustWordListMarginParser.js","sourceRoot":"","sources":["../../../../../packages/roosterjs-content-model-plugins/lib/paste/parsers/adjustWordListMarginParser.ts"],"names":[],"mappings":";;;;IAGA,IAAM,wBAAwB,GAAG,kBAAkB,CAAC;IAEpD,8FAA8F;IAC9F,IAAM,iCAAiC,GAAG,MAAM,CAAC;IAEjD;;;;;;OAMG;IACI,IAAM,0BAA0B,GAA+B,UAClE,MAAoB,EACpB,OAAoB;QAEpB,IAAI,OAAO,CAAC,SAAS,CAAC,QAAQ,CAAC,wBAAwB,CAAC,IAAI,MAAM,CAAC,UAAU,EAAE;YAC3E,IAAM,SAAS,GAAG,IAAA,gDAAkB,EAAC,MAAM,CAAC,UAAU,EAAE,OAAO,CAAC,CAAC;YACjE,IAAM,SAAS,GAAG,IAAA,gDAAkB,EAAC,iCAAiC,CAAC,CAAC;YACxE,IAAM,MAAM,GAAG,SAAS,GAAG,SAAS,CAAC;YAErC,IAAI,MAAM,GAAG,CAAC,EAAE;gBACZ,MAAM,CAAC,UAAU,GAAM,MAAM,OAAI,CAAC;aACrC;SACJ;IACL,CAAC,CAAC;IAbW,QAAA,0BAA0B,8BAarC","sourcesContent":["import { parseValueWithUnit } from 'roosterjs-content-model-dom';\nimport type { FormatParser, MarginFormat } from 'roosterjs-content-model-types';\n\nconst MSO_LIST_PARAGRAPH_CLASS = 'MsoListParagraph';\n\n// Default list padding from the HTML user-agent stylesheet (paddingInlineStart for <ul>/<ol>)\nconst DEFAULT_LIST_PADDING_INLINE_START = '40px';\n\n/**\n * @internal\n * Parser that subtracts the default list format (paddingInlineStart: 40px) from\n * the marginLeft of list item elements that have the MsoListParagraph class,\n * since Word adds the full indentation as margin on the paragraph, which\n * duplicates the padding the list element already provides.\n */\nexport const adjustWordListMarginParser: FormatParser<MarginFormat> = (\n format: MarginFormat,\n element: HTMLElement\n): void => {\n if (element.classList.contains(MSO_LIST_PARAGRAPH_CLASS) && format.marginLeft) {\n const currentPx = parseValueWithUnit(format.marginLeft, element);\n const defaultPx = parseValueWithUnit(DEFAULT_LIST_PADDING_INLINE_START);\n const result = currentPx - defaultPx;\n\n if (result > 0) {\n format.marginLeft = `${result}px`;\n }\n }\n};\n"]}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
define(["require", "exports", "tslib", "../../../pluginUtils/CreateElement/createElement", "../../../pluginUtils/DragAndDrop/DragAndDropHelper", "roosterjs-content-model-api", "../utils/getTableFromContentModel", "
|
|
1
|
+
define(["require", "exports", "tslib", "../../../pluginUtils/CreateElement/createElement", "../../../pluginUtils/DragAndDrop/DragAndDropHelper", "roosterjs-content-model-api", "../utils/getTableFromContentModel", "roosterjs-content-model-dom"], function (require, exports, tslib_1, createElement_1, DragAndDropHelper_1, roosterjs_content_model_api_1, getTableFromContentModel_1, roosterjs_content_model_dom_1) {
|
|
2
2
|
"use strict";
|
|
3
3
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
4
4
|
exports.onDragEnd = exports.onDragging = exports.onDragStart = exports.createTableMover = exports.TABLE_MOVER_ID = void 0;
|
|
@@ -128,7 +128,7 @@ define(["require", "exports", "tslib", "../../../pluginUtils/CreateElement/creat
|
|
|
128
128
|
// Move table outline rectangle
|
|
129
129
|
tableRect.style.top = event.clientY + TABLE_MOVER_LENGTH + "px";
|
|
130
130
|
tableRect.style.left = event.clientX + TABLE_MOVER_LENGTH + "px";
|
|
131
|
-
var pos = (0,
|
|
131
|
+
var pos = (0, roosterjs_content_model_dom_1.getNodePositionFromEvent)(editor.getDocument(), editor.getDOMHelper(), event.clientX, event.clientY);
|
|
132
132
|
if (pos) {
|
|
133
133
|
var range = editor.getDocument().createRange();
|
|
134
134
|
range.setStart(pos.node, pos.offset);
|
|
@@ -168,7 +168,7 @@ define(["require", "exports", "tslib", "../../../pluginUtils/CreateElement/creat
|
|
|
168
168
|
}
|
|
169
169
|
var insertionSuccess_1 = false;
|
|
170
170
|
// Get position to insert table
|
|
171
|
-
var insertPosition = (0,
|
|
171
|
+
var insertPosition = (0, roosterjs_content_model_dom_1.getNodePositionFromEvent)(editor.getDocument(), editor.getDOMHelper(), event.clientX, event.clientY);
|
|
172
172
|
if (insertPosition) {
|
|
173
173
|
// Move table to new position
|
|
174
174
|
(0, roosterjs_content_model_api_1.formatInsertPointWithContentModel)(editor, insertPosition, function (model, context, ip) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"TableMover.js","sourceRoot":"","sources":["../../../../../../packages/roosterjs-content-model-plugins/lib/tableEdit/editors/features/TableMover.ts"],"names":[],"mappings":"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","sourcesContent":["import { createElement } from '../../../pluginUtils/CreateElement/createElement';\nimport { DragAndDropHelper } from '../../../pluginUtils/DragAndDrop/DragAndDropHelper';\nimport { formatInsertPointWithContentModel } from 'roosterjs-content-model-api';\nimport { getCMTableFromTable } from '../utils/getTableFromContentModel';\nimport { getNodePositionFromEvent } from '../../../utils/getNodePositionFromEvent';\nimport type { TableEditFeature } from './TableEditFeature';\nimport type { OnTableEditorCreatedCallback } from '../../OnTableEditorCreatedCallback';\nimport type { DragAndDropHandler } from '../../../pluginUtils/DragAndDrop/DragAndDropHandler';\nimport {\n cloneModel,\n createContentModelDocument,\n createSelectionMarker,\n getFirstSelectedTable,\n isNodeOfType,\n mergeModel,\n mutateBlock,\n normalizeRect,\n setParagraphNotImplicit,\n setSelection,\n} from 'roosterjs-content-model-dom';\nimport type {\n DOMSelection,\n IEditor,\n ReadonlyContentModelTable,\n Rect,\n ShallowMutableContentModelDocument,\n} from 'roosterjs-content-model-types';\n\nconst TABLE_MOVER_LENGTH = 12;\n/**\n * @internal\n */\nexport const TABLE_MOVER_ID = '_Table_Mover';\nconst TABLE_MOVER_STYLE_KEY = '_TableMoverCursorStyle';\n\n/**\n * @internal\n * Allows user to move table to another position\n * Contains the function to select whole table\n */\nexport function createTableMover(\n table: HTMLTableElement,\n editor: IEditor,\n isRTL: boolean,\n onFinishDragging: (table: HTMLTableElement) => void,\n onStart: () => void,\n onEnd: (disposeHandler: boolean) => void,\n contentDiv?: EventTarget | null,\n anchorContainer?: HTMLElement,\n onTableEditorCreated?: OnTableEditorCreatedCallback,\n disableMovement?: boolean\n): TableEditFeature | null {\n const rect = normalizeRect(table.getBoundingClientRect());\n\n if (!isTableTopVisible(editor, rect, contentDiv as Node)) {\n return null;\n }\n\n const zoomScale = editor.getDOMHelper().calculateZoomScale();\n const document = table.ownerDocument;\n const createElementData = {\n tag: 'div',\n style: 'position: fixed; cursor: move; user-select: none; border: 1px solid #808080',\n };\n\n const div = createElement(createElementData, document) as HTMLDivElement;\n\n div.id = TABLE_MOVER_ID;\n div.style.width = `${TABLE_MOVER_LENGTH}px`;\n div.style.height = `${TABLE_MOVER_LENGTH}px`;\n\n (anchorContainer || document.body).appendChild(div);\n\n const context: TableMoverContext = {\n table,\n zoomScale,\n rect,\n isRTL,\n editor,\n div,\n onFinishDragging,\n onStart,\n onEnd,\n disableMovement,\n };\n\n setDivPosition(context, div);\n\n const featureHandler = new TableMoverFeature(\n div,\n context,\n () => {},\n disableMovement\n ? { onDragEnd }\n : {\n onDragStart,\n onDragging,\n onDragEnd,\n },\n context.zoomScale,\n onTableEditorCreated,\n editor.getEnvironment().isMobileOrTablet\n );\n\n return { node: table, div, featureHandler };\n}\n\n/**\n * @internal\n * Exported for testing\n */\nexport interface TableMoverContext {\n table: HTMLTableElement;\n zoomScale: number;\n rect: Rect | null;\n isRTL: boolean;\n editor: IEditor;\n div: HTMLElement;\n onFinishDragging: (table: HTMLTableElement) => void;\n onStart: () => void;\n onEnd: (disposeHandler: boolean) => void;\n disableMovement?: boolean;\n}\n\n/**\n * @internal\n * Exported for testing\n */\nexport interface TableMoverInitValue {\n cmTable: ReadonlyContentModelTable | undefined;\n initialSelection: DOMSelection | null;\n tableRect: HTMLDivElement;\n}\n\nclass TableMoverFeature extends DragAndDropHelper<TableMoverContext, TableMoverInitValue> {\n private disposer: undefined | (() => void);\n\n constructor(\n div: HTMLElement,\n context: TableMoverContext,\n onSubmit: (\n context: TableMoverContext,\n trigger: HTMLElement,\n container?: HTMLElement\n ) => void,\n handler: DragAndDropHandler<TableMoverContext, TableMoverInitValue>,\n zoomScale: number,\n onTableEditorCreated?: OnTableEditorCreatedCallback,\n forceMobile?: boolean | undefined\n ) {\n super(div, context, onSubmit, handler, zoomScale, forceMobile);\n this.disposer = onTableEditorCreated?.('TableMover', div);\n }\n\n dispose(): void {\n this.disposer?.();\n this.disposer = undefined;\n super.dispose();\n }\n}\n\nfunction setDivPosition(context: TableMoverContext, trigger: HTMLElement) {\n const { rect } = context;\n if (rect) {\n trigger.style.top = `${rect.top - TABLE_MOVER_LENGTH}px`;\n trigger.style.left = `${rect.left - TABLE_MOVER_LENGTH - 2}px`;\n }\n}\n\nfunction isTableTopVisible(editor: IEditor, rect: Rect | null, contentDiv?: Node | null): boolean {\n const visibleViewport = editor.getVisibleViewport();\n if (isNodeOfType(contentDiv, 'ELEMENT_NODE') && visibleViewport && rect) {\n const containerRect = normalizeRect(contentDiv.getBoundingClientRect());\n\n return !!containerRect && containerRect.top <= rect.top && visibleViewport.top <= rect.top;\n }\n\n return true;\n}\n\nfunction setTableMoverCursor(editor: IEditor, state: boolean, type?: 'move' | 'copy') {\n editor?.setEditorStyle(TABLE_MOVER_STYLE_KEY, state ? 'cursor: ' + type ?? 'move' : null);\n}\n\n/**\n * @internal\n * Exported for testing\n */\nexport function onDragStart(context: TableMoverContext): TableMoverInitValue {\n context.onStart();\n\n const { editor, table, div } = context;\n\n setTableMoverCursor(editor, true, 'move');\n\n // Create table outline rectangle\n const trect = table.getBoundingClientRect();\n const createElementData = {\n tag: 'div',\n style: 'position: fixed; user-select: none; border: 1px solid #808080',\n };\n const tableRect = createElement(createElementData, editor.getDocument()) as HTMLDivElement;\n tableRect.style.width = `${trect.width}px`;\n tableRect.style.height = `${trect.height}px`;\n tableRect.style.top = `${trect.top}px`;\n tableRect.style.left = `${trect.left}px`;\n div.parentNode?.appendChild(tableRect);\n\n // Get drag start selection\n const initialSelection = editor.getDOMSelection();\n\n // Get Table block in content model\n const cmTable = getCMTableFromTable(editor, table);\n\n return {\n cmTable,\n initialSelection,\n tableRect,\n };\n}\n\n/**\n * @internal\n * Exported for testing\n */\nexport function onDragging(\n context: TableMoverContext,\n event: MouseEvent,\n initValue: TableMoverInitValue\n) {\n const { tableRect } = initValue;\n const { editor } = context;\n\n // Move table outline rectangle\n tableRect.style.top = `${event.clientY + TABLE_MOVER_LENGTH}px`;\n tableRect.style.left = `${event.clientX + TABLE_MOVER_LENGTH}px`;\n\n const pos = getNodePositionFromEvent(editor, event.clientX, event.clientY);\n if (pos) {\n const range = editor.getDocument().createRange();\n range.setStart(pos.node, pos.offset);\n range.collapse(true);\n\n editor.setDOMSelection({ type: 'range', range, isReverted: false });\n return true;\n }\n return false;\n}\n\n/**\n * @internal\n * Exported for testing\n */\nexport function onDragEnd(\n context: TableMoverContext,\n event: MouseEvent,\n initValue: TableMoverInitValue | undefined\n) {\n const { editor, table, onFinishDragging: selectWholeTable, disableMovement } = context;\n const element = event.target;\n\n // Remove table outline rectangle\n initValue?.tableRect.remove();\n\n // Reset cursor\n setTableMoverCursor(editor, false);\n\n if (element == context.div) {\n // Table mover was only clicked, select whole table and do not dismiss the handler element.\n selectWholeTable(table);\n context.onEnd(false /* disposeHandler */);\n return true;\n } else {\n // Check if table was dragged on itself, element is not in editor, or movement is disabled\n if (\n table.contains(element as Node) ||\n !editor.getDOMHelper().isNodeInEditor(element as Node) ||\n disableMovement\n ) {\n editor.setDOMSelection(initValue?.initialSelection ?? null);\n context.onEnd(true /* disposeHandler */);\n return false;\n }\n\n let insertionSuccess: boolean = false;\n\n // Get position to insert table\n const insertPosition = getNodePositionFromEvent(editor, event.clientX, event.clientY);\n if (insertPosition) {\n // Move table to new position\n formatInsertPointWithContentModel(\n editor,\n insertPosition,\n (model, context, ip) => {\n // Remove old table\n const [oldTable, path] = getFirstSelectedTable(model);\n if (oldTable) {\n const index = path[0].blocks.indexOf(oldTable);\n mutateBlock(path[0]).blocks.splice(index, 1);\n }\n\n if (ip && initValue?.cmTable) {\n // Insert new table\n const doc: ShallowMutableContentModelDocument = createContentModelDocument();\n doc.blocks.push(oldTable ?? mutateBlock(initValue.cmTable));\n insertionSuccess = !!mergeModel(model, cloneModel(doc), context, {\n mergeFormat: 'none',\n insertPosition: ip,\n });\n\n if (insertionSuccess) {\n // After mergeModel, the new table should be selected\n const finalTable = getFirstSelectedTable(model)[0] ?? initValue.cmTable;\n if (finalTable) {\n // Add selection marker to the first cell of the table\n const firstCell = finalTable.rows[0].cells[0];\n const markerParagraph = firstCell?.blocks[0];\n\n if (markerParagraph?.blockType == 'Paragraph') {\n const marker = createSelectionMarker(model.format);\n\n mutateBlock(markerParagraph).segments.unshift(marker);\n setParagraphNotImplicit(markerParagraph);\n setSelection(model, marker);\n }\n }\n }\n return insertionSuccess;\n }\n },\n {\n // Select first cell of the old table\n selectionOverride: {\n type: 'table',\n firstColumn: 0,\n firstRow: 0,\n lastColumn: 0,\n lastRow: 0,\n table: table,\n },\n apiName: 'TableMover',\n }\n );\n } else {\n // No movement, restore initial selection\n editor.setDOMSelection(initValue?.initialSelection ?? null);\n }\n context.onEnd(true /* disposeHandler */);\n return insertionSuccess;\n }\n}\n"]}
|
|
1
|
+
{"version":3,"file":"TableMover.js","sourceRoot":"","sources":["../../../../../../packages/roosterjs-content-model-plugins/lib/tableEdit/editors/features/TableMover.ts"],"names":[],"mappings":"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","sourcesContent":["import { createElement } from '../../../pluginUtils/CreateElement/createElement';\nimport { DragAndDropHelper } from '../../../pluginUtils/DragAndDrop/DragAndDropHelper';\nimport { formatInsertPointWithContentModel } from 'roosterjs-content-model-api';\nimport { getCMTableFromTable } from '../utils/getTableFromContentModel';\nimport {\n cloneModel,\n createContentModelDocument,\n createSelectionMarker,\n getFirstSelectedTable,\n getNodePositionFromEvent,\n isNodeOfType,\n mergeModel,\n mutateBlock,\n normalizeRect,\n setParagraphNotImplicit,\n setSelection,\n} from 'roosterjs-content-model-dom';\nimport type { TableEditFeature } from './TableEditFeature';\nimport type { OnTableEditorCreatedCallback } from '../../OnTableEditorCreatedCallback';\nimport type { DragAndDropHandler } from '../../../pluginUtils/DragAndDrop/DragAndDropHandler';\nimport type {\n DOMSelection,\n IEditor,\n ReadonlyContentModelTable,\n Rect,\n ShallowMutableContentModelDocument,\n} from 'roosterjs-content-model-types';\n\nconst TABLE_MOVER_LENGTH = 12;\n/**\n * @internal\n */\nexport const TABLE_MOVER_ID = '_Table_Mover';\nconst TABLE_MOVER_STYLE_KEY = '_TableMoverCursorStyle';\n\n/**\n * @internal\n * Allows user to move table to another position\n * Contains the function to select whole table\n */\nexport function createTableMover(\n table: HTMLTableElement,\n editor: IEditor,\n isRTL: boolean,\n onFinishDragging: (table: HTMLTableElement) => void,\n onStart: () => void,\n onEnd: (disposeHandler: boolean) => void,\n contentDiv?: EventTarget | null,\n anchorContainer?: HTMLElement,\n onTableEditorCreated?: OnTableEditorCreatedCallback,\n disableMovement?: boolean\n): TableEditFeature | null {\n const rect = normalizeRect(table.getBoundingClientRect());\n\n if (!isTableTopVisible(editor, rect, contentDiv as Node)) {\n return null;\n }\n\n const zoomScale = editor.getDOMHelper().calculateZoomScale();\n const document = table.ownerDocument;\n const createElementData = {\n tag: 'div',\n style: 'position: fixed; cursor: move; user-select: none; border: 1px solid #808080',\n };\n\n const div = createElement(createElementData, document) as HTMLDivElement;\n\n div.id = TABLE_MOVER_ID;\n div.style.width = `${TABLE_MOVER_LENGTH}px`;\n div.style.height = `${TABLE_MOVER_LENGTH}px`;\n\n (anchorContainer || document.body).appendChild(div);\n\n const context: TableMoverContext = {\n table,\n zoomScale,\n rect,\n isRTL,\n editor,\n div,\n onFinishDragging,\n onStart,\n onEnd,\n disableMovement,\n };\n\n setDivPosition(context, div);\n\n const featureHandler = new TableMoverFeature(\n div,\n context,\n () => {},\n disableMovement\n ? { onDragEnd }\n : {\n onDragStart,\n onDragging,\n onDragEnd,\n },\n context.zoomScale,\n onTableEditorCreated,\n editor.getEnvironment().isMobileOrTablet\n );\n\n return { node: table, div, featureHandler };\n}\n\n/**\n * @internal\n * Exported for testing\n */\nexport interface TableMoverContext {\n table: HTMLTableElement;\n zoomScale: number;\n rect: Rect | null;\n isRTL: boolean;\n editor: IEditor;\n div: HTMLElement;\n onFinishDragging: (table: HTMLTableElement) => void;\n onStart: () => void;\n onEnd: (disposeHandler: boolean) => void;\n disableMovement?: boolean;\n}\n\n/**\n * @internal\n * Exported for testing\n */\nexport interface TableMoverInitValue {\n cmTable: ReadonlyContentModelTable | undefined;\n initialSelection: DOMSelection | null;\n tableRect: HTMLDivElement;\n}\n\nclass TableMoverFeature extends DragAndDropHelper<TableMoverContext, TableMoverInitValue> {\n private disposer: undefined | (() => void);\n\n constructor(\n div: HTMLElement,\n context: TableMoverContext,\n onSubmit: (\n context: TableMoverContext,\n trigger: HTMLElement,\n container?: HTMLElement\n ) => void,\n handler: DragAndDropHandler<TableMoverContext, TableMoverInitValue>,\n zoomScale: number,\n onTableEditorCreated?: OnTableEditorCreatedCallback,\n forceMobile?: boolean | undefined\n ) {\n super(div, context, onSubmit, handler, zoomScale, forceMobile);\n this.disposer = onTableEditorCreated?.('TableMover', div);\n }\n\n dispose(): void {\n this.disposer?.();\n this.disposer = undefined;\n super.dispose();\n }\n}\n\nfunction setDivPosition(context: TableMoverContext, trigger: HTMLElement) {\n const { rect } = context;\n if (rect) {\n trigger.style.top = `${rect.top - TABLE_MOVER_LENGTH}px`;\n trigger.style.left = `${rect.left - TABLE_MOVER_LENGTH - 2}px`;\n }\n}\n\nfunction isTableTopVisible(editor: IEditor, rect: Rect | null, contentDiv?: Node | null): boolean {\n const visibleViewport = editor.getVisibleViewport();\n if (isNodeOfType(contentDiv, 'ELEMENT_NODE') && visibleViewport && rect) {\n const containerRect = normalizeRect(contentDiv.getBoundingClientRect());\n\n return !!containerRect && containerRect.top <= rect.top && visibleViewport.top <= rect.top;\n }\n\n return true;\n}\n\nfunction setTableMoverCursor(editor: IEditor, state: boolean, type?: 'move' | 'copy') {\n editor?.setEditorStyle(TABLE_MOVER_STYLE_KEY, state ? 'cursor: ' + type ?? 'move' : null);\n}\n\n/**\n * @internal\n * Exported for testing\n */\nexport function onDragStart(context: TableMoverContext): TableMoverInitValue {\n context.onStart();\n\n const { editor, table, div } = context;\n\n setTableMoverCursor(editor, true, 'move');\n\n // Create table outline rectangle\n const trect = table.getBoundingClientRect();\n const createElementData = {\n tag: 'div',\n style: 'position: fixed; user-select: none; border: 1px solid #808080',\n };\n const tableRect = createElement(createElementData, editor.getDocument()) as HTMLDivElement;\n tableRect.style.width = `${trect.width}px`;\n tableRect.style.height = `${trect.height}px`;\n tableRect.style.top = `${trect.top}px`;\n tableRect.style.left = `${trect.left}px`;\n div.parentNode?.appendChild(tableRect);\n\n // Get drag start selection\n const initialSelection = editor.getDOMSelection();\n\n // Get Table block in content model\n const cmTable = getCMTableFromTable(editor, table);\n\n return {\n cmTable,\n initialSelection,\n tableRect,\n };\n}\n\n/**\n * @internal\n * Exported for testing\n */\nexport function onDragging(\n context: TableMoverContext,\n event: MouseEvent,\n initValue: TableMoverInitValue\n) {\n const { tableRect } = initValue;\n const { editor } = context;\n\n // Move table outline rectangle\n tableRect.style.top = `${event.clientY + TABLE_MOVER_LENGTH}px`;\n tableRect.style.left = `${event.clientX + TABLE_MOVER_LENGTH}px`;\n\n const pos = getNodePositionFromEvent(\n editor.getDocument(),\n editor.getDOMHelper(),\n event.clientX,\n event.clientY\n );\n if (pos) {\n const range = editor.getDocument().createRange();\n range.setStart(pos.node, pos.offset);\n range.collapse(true);\n\n editor.setDOMSelection({ type: 'range', range, isReverted: false });\n return true;\n }\n return false;\n}\n\n/**\n * @internal\n * Exported for testing\n */\nexport function onDragEnd(\n context: TableMoverContext,\n event: MouseEvent,\n initValue: TableMoverInitValue | undefined\n) {\n const { editor, table, onFinishDragging: selectWholeTable, disableMovement } = context;\n const element = event.target;\n\n // Remove table outline rectangle\n initValue?.tableRect.remove();\n\n // Reset cursor\n setTableMoverCursor(editor, false);\n\n if (element == context.div) {\n // Table mover was only clicked, select whole table and do not dismiss the handler element.\n selectWholeTable(table);\n context.onEnd(false /* disposeHandler */);\n return true;\n } else {\n // Check if table was dragged on itself, element is not in editor, or movement is disabled\n if (\n table.contains(element as Node) ||\n !editor.getDOMHelper().isNodeInEditor(element as Node) ||\n disableMovement\n ) {\n editor.setDOMSelection(initValue?.initialSelection ?? null);\n context.onEnd(true /* disposeHandler */);\n return false;\n }\n\n let insertionSuccess: boolean = false;\n\n // Get position to insert table\n const insertPosition = getNodePositionFromEvent(\n editor.getDocument(),\n editor.getDOMHelper(),\n event.clientX,\n event.clientY\n );\n if (insertPosition) {\n // Move table to new position\n formatInsertPointWithContentModel(\n editor,\n insertPosition,\n (model, context, ip) => {\n // Remove old table\n const [oldTable, path] = getFirstSelectedTable(model);\n if (oldTable) {\n const index = path[0].blocks.indexOf(oldTable);\n mutateBlock(path[0]).blocks.splice(index, 1);\n }\n\n if (ip && initValue?.cmTable) {\n // Insert new table\n const doc: ShallowMutableContentModelDocument = createContentModelDocument();\n doc.blocks.push(oldTable ?? mutateBlock(initValue.cmTable));\n insertionSuccess = !!mergeModel(model, cloneModel(doc), context, {\n mergeFormat: 'none',\n insertPosition: ip,\n });\n\n if (insertionSuccess) {\n // After mergeModel, the new table should be selected\n const finalTable = getFirstSelectedTable(model)[0] ?? initValue.cmTable;\n if (finalTable) {\n // Add selection marker to the first cell of the table\n const firstCell = finalTable.rows[0].cells[0];\n const markerParagraph = firstCell?.blocks[0];\n\n if (markerParagraph?.blockType == 'Paragraph') {\n const marker = createSelectionMarker(model.format);\n\n mutateBlock(markerParagraph).segments.unshift(marker);\n setParagraphNotImplicit(markerParagraph);\n setSelection(model, marker);\n }\n }\n }\n return insertionSuccess;\n }\n },\n {\n // Select first cell of the old table\n selectionOverride: {\n type: 'table',\n firstColumn: 0,\n firstRow: 0,\n lastColumn: 0,\n lastRow: 0,\n table: table,\n },\n apiName: 'TableMover',\n }\n );\n } else {\n // No movement, restore initial selection\n editor.setDOMSelection(initValue?.initialSelection ?? null);\n }\n context.onEnd(true /* disposeHandler */);\n return insertionSuccess;\n }\n}\n"]}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
define(["require", "exports", "
|
|
1
|
+
define(["require", "exports", "roosterjs-content-model-dom"], function (require, exports, roosterjs_content_model_dom_1) {
|
|
2
2
|
"use strict";
|
|
3
3
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
4
4
|
exports.TouchPlugin = void 0;
|
|
@@ -69,7 +69,7 @@ define(["require", "exports", "../utils/getNodePositionFromEvent"], function (re
|
|
|
69
69
|
if (_this.editor) {
|
|
70
70
|
if (!_this.isDblClicked) {
|
|
71
71
|
_this.editor.focus();
|
|
72
|
-
var caretPosition = (0,
|
|
72
|
+
var caretPosition = (0, roosterjs_content_model_dom_1.getNodePositionFromEvent)(_this.editor.getDocument(), _this.editor.getDOMHelper(), event.rawEvent.x, event.rawEvent.y);
|
|
73
73
|
var newRange = _this.editor.getDocument().createRange();
|
|
74
74
|
if (caretPosition) {
|
|
75
75
|
var node = caretPosition.node, offset = caretPosition.offset;
|
|
@@ -117,7 +117,7 @@ define(["require", "exports", "../utils/getNodePositionFromEvent"], function (re
|
|
|
117
117
|
if (this.isTouchPenPointerEvent) {
|
|
118
118
|
event.rawEvent.preventDefault();
|
|
119
119
|
this.isDblClicked = true;
|
|
120
|
-
var caretPosition = (0,
|
|
120
|
+
var caretPosition = (0, roosterjs_content_model_dom_1.getNodePositionFromEvent)(this.editor.getDocument(), this.editor.getDOMHelper(), event.rawEvent.x, event.rawEvent.y);
|
|
121
121
|
if (caretPosition) {
|
|
122
122
|
var node = caretPosition.node, offset = caretPosition.offset;
|
|
123
123
|
if (node.nodeType !== Node.TEXT_NODE) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"TouchPlugin.js","sourceRoot":"","sources":["../../../../packages/roosterjs-content-model-plugins/lib/touch/TouchPlugin.ts"],"names":[],"mappings":";;;;IAGA,IAAM,uBAAuB,GAAG,CAAC,CAAC,CAAC,4DAA4D;IAC/F,IAAM,uBAAuB,GAAG,GAAG,CAAC,CAAC,6GAA6G;IAClJ,IAAM,0BAA0B,GAAG,SAAS,CAAC;IAC7C,IAAM,oBAAoB,GAAG,IAAI,CAAC;IAElC;;OAEG;IACH;QAMI;;WAEG;QACH;YARQ,WAAM,GAAmB,IAAI,CAAC;YAC9B,UAAK,GAAG,CAAC,CAAC;YACV,iBAAY,GAAY,KAAK,CAAC;YAC9B,2BAAsB,GAAY,KAAK,CAAC;QAKjC,CAAC;QAEhB;;WAEG;QACH,6BAAO,GAAP;YACI,OAAO,OAAO,CAAC;QACnB,CAAC;QAED;;;WAGG;QACH,gCAAU,GAAV,UAAW,MAAe;YACtB,IAAI,CAAC,MAAM,GAAG,MAAM,CAAC;YACrB,IAAI,CAAC,YAAY,GAAG,KAAK,CAAC;QAC9B,CAAC;QAED;;WAEG;QACH,6BAAO,GAAP;;YACI,IAAI,IAAI,CAAC,KAAK,EAAE;gBACZ,MAAA,MAAA,MAAA,IAAI,CAAC,MAAM,0CAAE,WAAW,EAAE,0CAAE,WAAW,0CAAE,YAAY,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;gBAClE,IAAI,CAAC,KAAK,GAAG,CAAC,CAAC;aAClB;YACD,IAAI,CAAC,MAAM,GAAG,IAAI,CAAC;QACvB,CAAC;QAED;;;WAGG;QACH,mCAAa,GAAb,UAAc,KAAkB;YAAhC,iBAqKC;;YApKG,IAAI,CAAC,IAAI,CAAC,MAAM,EAAE;gBACd,OAAO;aACV;YACD,QAAQ,KAAK,CAAC,SAAS,EAAE;gBACrB,KAAK,aAAa;oBACd,IAAI,CAAC,YAAY,GAAG,KAAK,CAAC;oBAC1B,IAAI,CAAC,sBAAsB,GAAG,IAAI,CAAC;oBACnC,KAAK,CAAC,aAAa,CAAC,cAAc,EAAE,CAAC;oBAErC,IAAM,YAAY,GAAG,IAAI,CAAC,MAAM,CAAC,WAAW,EAAE,CAAC,WAAW,CAAC;oBAE3D,IAAI,YAAY,EAAE;wBACd,IAAI,IAAI,CAAC,KAAK,EAAE;4BACZ,YAAY,CAAC,YAAY,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;yBACzC;wBAED,IAAI,CAAC,KAAK,GAAG,YAAY,CAAC,UAAU,CAAC;4BACjC,KAAI,CAAC,KAAK,GAAG,CAAC,CAAC;4BAEf,IAAI,KAAI,CAAC,MAAM,EAAE;gCACb,IAAI,CAAC,KAAI,CAAC,YAAY,EAAE;oCACpB,KAAI,CAAC,MAAM,CAAC,KAAK,EAAE,CAAC;oCACpB,IAAM,aAAa,GAAG,IAAA,mDAAwB,EAC1C,KAAI,CAAC,MAAM,EACX,KAAK,CAAC,QAAQ,CAAC,CAAC,EAChB,KAAK,CAAC,QAAQ,CAAC,CAAC,CACnB,CAAC;oCAEF,IAAM,QAAQ,GAAG,KAAI,CAAC,MAAM,CAAC,WAAW,EAAE,CAAC,WAAW,EAAE,CAAC;oCACzD,IAAI,aAAa,EAAE;wCACP,IAAA,IAAI,GAAa,aAAa,KAA1B,EAAE,MAAM,GAAK,aAAa,OAAlB,CAAmB;wCAEvC,8DAA8D;wCAC9D,QAAQ,CAAC,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC,CAAC;wCAChC,QAAQ,CAAC,MAAM,CAAC,IAAI,EAAE,MAAM,CAAC,CAAC;wCAE9B,IAAM,eAAe,GAAG,IAAI,CAAC,WAAW,IAAI,EAAE,CAAC;wCAC/C,IAAM,eAAe,GAAG,eAAe,CAAC,MAAM,CAAC,CAAC;wCAChD,IACI,IAAI,CAAC,QAAQ,KAAK,IAAI,CAAC,SAAS;4CAChC,eAAe;4CACf,CAAC,oBAAoB,CAAC,IAAI,CAAC,eAAe,CAAC;4CAC3C,CAAC,0BAA0B,CAAC,IAAI,CAAC,eAAe,CAAC,EACnD;4CACQ,IAAA,KAAyB,kBAAkB,CAC7C,eAAe,EACf,MAAM,CACT,EAHO,SAAS,eAAA,EAAE,OAAO,aAGzB,CAAC;4CAEF,uCAAuC;4CACvC,IAAM,oBAAoB,GAAG,MAAM,GAAG,SAAS,CAAC;4CAChD,IAAM,qBAAqB,GAAG,OAAO,GAAG,MAAM,CAAC;4CAC/C,IAAI,YAAY,GACZ,oBAAoB,IAAI,qBAAqB;gDACzC,CAAC,CAAC,qBAAqB;gDACvB,CAAC,CAAC,CAAC,oBAAoB,CAAC;4CAChC,YAAY;gDACR,IAAI,CAAC,GAAG,CAAC,YAAY,CAAC,GAAG,uBAAuB;oDAC5C,CAAC,CAAC,CAAC;oDACH,CAAC,CAAC,YAAY,CAAC;4CACvB,IAAM,iBAAiB,GAAG,MAAM,GAAG,YAAY,CAAC;4CAChD,IACI,YAAY,KAAK,CAAC;gDAClB,eAAe,CAAC,MAAM,IAAI,iBAAiB,EAC7C;gDACE,QAAQ,CAAC,QAAQ,CAAC,IAAI,EAAE,iBAAiB,CAAC,CAAC;gDAC3C,QAAQ,CAAC,MAAM,CAAC,IAAI,EAAE,iBAAiB,CAAC,CAAC;6CAC5C;yCACJ;qCACJ;oCACD,KAAI,CAAC,MAAM,CAAC,eAAe,CAAC;wCACxB,IAAI,EAAE,OAAO;wCACb,KAAK,EAAE,QAAQ;wCACf,UAAU,EAAE,KAAK;qCACpB,CAAC,CAAC;oCAEH,eAAe;oCACf,KAAI,CAAC,sBAAsB,GAAG,KAAK,CAAC;iCACvC;6BACJ;wBACL,CAAC,EAAE,uBAAuB,CAAC,CAAC;qBAC/B;oBACD,MAAM;gBACV,KAAK,aAAa;oBACd,IAAI,IAAI,CAAC,sBAAsB,EAAE;wBAC7B,KAAK,CAAC,QAAQ,CAAC,cAAc,EAAE,CAAC;wBAEhC,IAAI,CAAC,YAAY,GAAG,IAAI,CAAC;wBACzB,IAAM,aAAa,GAAG,IAAA,mDAAwB,EAC1C,IAAI,CAAC,MAAM,EACX,KAAK,CAAC,QAAQ,CAAC,CAAC,EAChB,KAAK,CAAC,QAAQ,CAAC,CAAC,CACnB,CAAC;wBAEF,IAAI,aAAa,EAAE;4BACP,IAAA,IAAI,GAAa,aAAa,KAA1B,EAAE,MAAM,GAAK,aAAa,OAAlB,CAAmB;4BAEvC,IAAI,IAAI,CAAC,QAAQ,KAAK,IAAI,CAAC,SAAS,EAAE;gCAClC,OAAO;6BACV;4BAED,IAAM,eAAe,GAAG,IAAI,CAAC,SAAS,IAAI,EAAE,CAAC;4BAC7C,IAAM,IAAI,GAAG,eAAe,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC;4BAE5C,2FAA2F;4BAC3F,IAAI,0BAA0B,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE;gCACvC,IAAM,QAAQ,GAAG,MAAA,IAAI,CAAC,MAAM,CAAC,WAAW,EAAE,0CAAE,WAAW,EAAE,CAAC;gCAC1D,IAAI,QAAQ,EAAE;oCACV,QAAQ,CAAC,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC,CAAC;oCAChC,QAAQ,CAAC,MAAM,CAAC,IAAI,EAAE,MAAM,GAAG,CAAC,CAAC,CAAC;oCAClC,IAAI,CAAC,MAAM,CAAC,eAAe,CAAC;wCACxB,IAAI,EAAE,OAAO;wCACb,KAAK,EAAE,QAAQ;wCACf,UAAU,EAAE,KAAK;qCACpB,CAAC,CAAC;iCACN;6BACJ;iCAAM,IAAI,oBAAoB,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE;gCACxC,uEAAuE;gCACvE,IAAM,eAAe,GAAG,eAAe,CAAC,SAAS,CAC7C,MAAM,EACN,eAAe,CAAC,MAAM,CACzB,CAAC;gCACF,IAAM,oBAAoB,GACtB,eAAe,CAAC,MAAM,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,eAAe,CAAC,CAAC;gCAC9D,IAAI,oBAAoB,EAAE;oCACtB,8BAA8B;oCAC9B,IAAI,KAAK,GAAG,MAAM,CAAC;oCACnB,OACI,KAAK,GAAG,CAAC;wCACT,oBAAoB,CAAC,IAAI,CAAC,eAAe,CAAC,MAAM,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC,EAC9D;wCACE,KAAK,EAAE,CAAC;qCACX;oCACD,IAAM,QAAQ,GAAG,MAAA,IAAI,CAAC,MAAM,CAAC,WAAW,EAAE,0CAAE,WAAW,EAAE,CAAC;oCAC1D,IAAI,QAAQ,EAAE;wCACV,QAAQ,CAAC,QAAQ,CAAC,IAAI,EAAE,KAAK,CAAC,CAAC;wCAC/B,QAAQ,CAAC,MAAM,CAAC,IAAI,EAAE,KAAK,GAAG,CAAC,CAAC,CAAC;wCACjC,IAAI,CAAC,MAAM,CAAC,eAAe,CAAC;4CACxB,IAAI,EAAE,OAAO;4CACb,KAAK,EAAE,QAAQ;4CACf,UAAU,EAAE,KAAK;yCACpB,CAAC,CAAC;qCACN;iCACJ;6BACJ;iCAAM;gCACG,IAAA,KAAyB,kBAAkB,CAC7C,eAAe,EACf,MAAM,CACT,EAHO,SAAS,eAAA,EAAE,OAAO,aAGzB,CAAC;gCACF,IAAM,QAAQ,GAAG,MAAA,IAAI,CAAC,MAAM,CAAC,WAAW,EAAE,0CAAE,WAAW,EAAE,CAAC;gCAC1D,IAAI,QAAQ,EAAE;oCACV,QAAQ,CAAC,QAAQ,CAAC,IAAI,EAAE,SAAS,CAAC,CAAC;oCACnC,QAAQ,CAAC,MAAM,CAAC,IAAI,EAAE,OAAO,CAAC,CAAC;oCAC/B,IAAI,CAAC,MAAM,CAAC,eAAe,CAAC;wCACxB,IAAI,EAAE,OAAO;wCACb,KAAK,EAAE,QAAQ;wCACf,UAAU,EAAE,KAAK;qCACpB,CAAC,CAAC;iCACN;6BACJ;yBACJ;qBACJ;oBACD,MAAM;aACb;QACL,CAAC;QACL,kBAAC;IAAD,CAAC,AAhND,IAgNC;IAhNY,kCAAW;IAkNxB;;;;;;OAMG;IACH,SAAS,kBAAkB,CAAC,IAAY,EAAE,MAAc;QACpD,IAAI,KAAK,GAAG,MAAM,CAAC;QACnB,IAAI,GAAG,GAAG,MAAM,CAAC;QAEjB,0CAA0C;QAC1C,OACI,KAAK,GAAG,CAAC;YACT,CAAC,oBAAoB,CAAC,IAAI,CAAC,IAAI,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC;YAC3C,CAAC,0BAA0B,CAAC,IAAI,CAAC,IAAI,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC,EACnD;YACE,KAAK,EAAE,CAAC;SACX;QAED,oCAAoC;QACpC,OACI,GAAG,GAAG,IAAI,CAAC,MAAM;YACjB,CAAC,oBAAoB,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;YACrC,CAAC,0BAA0B,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,EAC7C;YACE,GAAG,EAAE,CAAC;SACT;QAED,OAAO;YACH,SAAS,EAAE,KAAK;YAChB,OAAO,EAAE,GAAG;SACf,CAAC;IACN,CAAC","sourcesContent":["import { getNodePositionFromEvent } from '../utils/getNodePositionFromEvent';\nimport type { EditorPlugin, IEditor, PluginEvent } from 'roosterjs-content-model-types';\n\nconst MAX_TOUCH_MOVE_DISTANCE = 6; // the max number of offsets for the touch selection to move\nconst POINTER_DETECTION_DELAY = 150; // Delay time to wait for selection to be updated and also detect if pointerup is a tap or part of double tap\nconst PUNCTUATION_MATCHING_REGEX = /[.,;:!]/;\nconst SPACE_MATCHING_REGEX = /\\s/;\n\n/**\n * Touch plugin to manage touch behaviors\n */\nexport class TouchPlugin implements EditorPlugin {\n private editor: IEditor | null = null;\n private timer = 0;\n private isDblClicked: boolean = false;\n private isTouchPenPointerEvent: boolean = false;\n\n /**\n * Create an instance of Touch plugin\n */\n constructor() {}\n\n /**\n * Get a friendly name of this plugin\n */\n getName() {\n return 'Touch';\n }\n\n /**\n * Initialize this plugin. This should only be called from Editor\n * @param editor Editor instance\n */\n initialize(editor: IEditor) {\n this.editor = editor;\n this.isDblClicked = false;\n }\n\n /**\n * Dispose this plugin\n */\n dispose() {\n if (this.timer) {\n this.editor?.getDocument()?.defaultView?.clearTimeout(this.timer);\n this.timer = 0;\n }\n this.editor = null;\n }\n\n /**\n * Handle events triggered from editor\n * @param event PluginEvent object\n */\n onPluginEvent(event: PluginEvent) {\n if (!this.editor) {\n return;\n }\n switch (event.eventType) {\n case 'pointerDown':\n this.isDblClicked = false;\n this.isTouchPenPointerEvent = true;\n event.originalEvent.preventDefault();\n\n const targetWindow = this.editor.getDocument().defaultView;\n\n if (targetWindow) {\n if (this.timer) {\n targetWindow.clearTimeout(this.timer);\n }\n\n this.timer = targetWindow.setTimeout(() => {\n this.timer = 0;\n\n if (this.editor) {\n if (!this.isDblClicked) {\n this.editor.focus();\n const caretPosition = getNodePositionFromEvent(\n this.editor,\n event.rawEvent.x,\n event.rawEvent.y\n );\n\n const newRange = this.editor.getDocument().createRange();\n if (caretPosition) {\n const { node, offset } = caretPosition;\n\n // Place cursor at same position of browser handler by default\n newRange.setStart(node, offset);\n newRange.setEnd(node, offset);\n\n const nodeTextContent = node.textContent || '';\n const charAtSelection = nodeTextContent[offset];\n if (\n node.nodeType === Node.TEXT_NODE &&\n charAtSelection &&\n !SPACE_MATCHING_REGEX.test(charAtSelection) &&\n !PUNCTUATION_MATCHING_REGEX.test(charAtSelection)\n ) {\n const { wordStart, wordEnd } = findWordBoundaries(\n nodeTextContent,\n offset\n );\n\n // Move cursor to the calculated offset\n const leftCursorWordLength = offset - wordStart;\n const rightCursorWordLength = wordEnd - offset;\n let movingOffset: number =\n leftCursorWordLength >= rightCursorWordLength\n ? rightCursorWordLength\n : -leftCursorWordLength;\n movingOffset =\n Math.abs(movingOffset) > MAX_TOUCH_MOVE_DISTANCE\n ? 0\n : movingOffset;\n const newOffsetPosition = offset + movingOffset;\n if (\n movingOffset !== 0 &&\n nodeTextContent.length >= newOffsetPosition\n ) {\n newRange.setStart(node, newOffsetPosition);\n newRange.setEnd(node, newOffsetPosition);\n }\n }\n }\n this.editor.setDOMSelection({\n type: 'range',\n range: newRange,\n isReverted: false,\n });\n\n // reset values\n this.isTouchPenPointerEvent = false;\n }\n }\n }, POINTER_DETECTION_DELAY);\n }\n break;\n case 'doubleClick':\n if (this.isTouchPenPointerEvent) {\n event.rawEvent.preventDefault();\n\n this.isDblClicked = true;\n const caretPosition = getNodePositionFromEvent(\n this.editor,\n event.rawEvent.x,\n event.rawEvent.y\n );\n\n if (caretPosition) {\n const { node, offset } = caretPosition;\n\n if (node.nodeType !== Node.TEXT_NODE) {\n return;\n }\n\n const nodeTextContent = node.nodeValue || '';\n const char = nodeTextContent.charAt(offset);\n\n // Check if the clicked character is a punctuation mark, then highlight that character only\n if (PUNCTUATION_MATCHING_REGEX.test(char)) {\n const newRange = this.editor.getDocument()?.createRange();\n if (newRange) {\n newRange.setStart(node, offset);\n newRange.setEnd(node, offset + 1);\n this.editor.setDOMSelection({\n type: 'range',\n range: newRange,\n isReverted: false,\n });\n }\n } else if (SPACE_MATCHING_REGEX.test(char)) {\n // If the clicked character is an open space with no word of right side\n const rightSideOfChar = nodeTextContent.substring(\n offset,\n nodeTextContent.length\n );\n const isRightSideAllSpaces =\n rightSideOfChar.length > 0 && !/\\S/.test(rightSideOfChar);\n if (isRightSideAllSpaces) {\n // select the first space only\n let start = offset;\n while (\n start > 0 &&\n SPACE_MATCHING_REGEX.test(nodeTextContent.charAt(start - 1))\n ) {\n start--;\n }\n const newRange = this.editor.getDocument()?.createRange();\n if (newRange) {\n newRange.setStart(node, start);\n newRange.setEnd(node, start + 1);\n this.editor.setDOMSelection({\n type: 'range',\n range: newRange,\n isReverted: false,\n });\n }\n }\n } else {\n const { wordStart, wordEnd } = findWordBoundaries(\n nodeTextContent,\n offset\n );\n const newRange = this.editor.getDocument()?.createRange();\n if (newRange) {\n newRange.setStart(node, wordStart);\n newRange.setEnd(node, wordEnd);\n this.editor.setDOMSelection({\n type: 'range',\n range: newRange,\n isReverted: false,\n });\n }\n }\n }\n }\n break;\n }\n }\n}\n\n/**\n * @internal\n * Finds the start and end indices of the word at the given offset in the text.\n * @param text The string to search within.\n * @param offset The index within the string to find the word boundaries around.\n * @returns An object containing wordStart and wordEnd indices.\n */\nfunction findWordBoundaries(text: string, offset: number) {\n let start = offset;\n let end = offset;\n\n // Move start backwards to find word start\n while (\n start > 0 &&\n !SPACE_MATCHING_REGEX.test(text[start - 1]) &&\n !PUNCTUATION_MATCHING_REGEX.test(text[start - 1])\n ) {\n start--;\n }\n\n // Move end forward to find word end\n while (\n end < text.length &&\n !SPACE_MATCHING_REGEX.test(text[end]) &&\n !PUNCTUATION_MATCHING_REGEX.test(text[end])\n ) {\n end++;\n }\n\n return {\n wordStart: start,\n wordEnd: end,\n };\n}\n"]}
|
|
1
|
+
{"version":3,"file":"TouchPlugin.js","sourceRoot":"","sources":["../../../../packages/roosterjs-content-model-plugins/lib/touch/TouchPlugin.ts"],"names":[],"mappings":"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","sourcesContent":["import { getNodePositionFromEvent } from 'roosterjs-content-model-dom';\nimport type { EditorPlugin, IEditor, PluginEvent } from 'roosterjs-content-model-types';\n\nconst MAX_TOUCH_MOVE_DISTANCE = 6; // the max number of offsets for the touch selection to move\nconst POINTER_DETECTION_DELAY = 150; // Delay time to wait for selection to be updated and also detect if pointerup is a tap or part of double tap\nconst PUNCTUATION_MATCHING_REGEX = /[.,;:!]/;\nconst SPACE_MATCHING_REGEX = /\\s/;\n\n/**\n * Touch plugin to manage touch behaviors\n */\nexport class TouchPlugin implements EditorPlugin {\n private editor: IEditor | null = null;\n private timer = 0;\n private isDblClicked: boolean = false;\n private isTouchPenPointerEvent: boolean = false;\n\n /**\n * Create an instance of Touch plugin\n */\n constructor() {}\n\n /**\n * Get a friendly name of this plugin\n */\n getName() {\n return 'Touch';\n }\n\n /**\n * Initialize this plugin. This should only be called from Editor\n * @param editor Editor instance\n */\n initialize(editor: IEditor) {\n this.editor = editor;\n this.isDblClicked = false;\n }\n\n /**\n * Dispose this plugin\n */\n dispose() {\n if (this.timer) {\n this.editor?.getDocument()?.defaultView?.clearTimeout(this.timer);\n this.timer = 0;\n }\n this.editor = null;\n }\n\n /**\n * Handle events triggered from editor\n * @param event PluginEvent object\n */\n onPluginEvent(event: PluginEvent) {\n if (!this.editor) {\n return;\n }\n switch (event.eventType) {\n case 'pointerDown':\n this.isDblClicked = false;\n this.isTouchPenPointerEvent = true;\n event.originalEvent.preventDefault();\n\n const targetWindow = this.editor.getDocument().defaultView;\n\n if (targetWindow) {\n if (this.timer) {\n targetWindow.clearTimeout(this.timer);\n }\n\n this.timer = targetWindow.setTimeout(() => {\n this.timer = 0;\n\n if (this.editor) {\n if (!this.isDblClicked) {\n this.editor.focus();\n const caretPosition = getNodePositionFromEvent(\n this.editor.getDocument(),\n this.editor.getDOMHelper(),\n event.rawEvent.x,\n event.rawEvent.y\n );\n\n const newRange = this.editor.getDocument().createRange();\n if (caretPosition) {\n const { node, offset } = caretPosition;\n\n // Place cursor at same position of browser handler by default\n newRange.setStart(node, offset);\n newRange.setEnd(node, offset);\n\n const nodeTextContent = node.textContent || '';\n const charAtSelection = nodeTextContent[offset];\n if (\n node.nodeType === Node.TEXT_NODE &&\n charAtSelection &&\n !SPACE_MATCHING_REGEX.test(charAtSelection) &&\n !PUNCTUATION_MATCHING_REGEX.test(charAtSelection)\n ) {\n const { wordStart, wordEnd } = findWordBoundaries(\n nodeTextContent,\n offset\n );\n\n // Move cursor to the calculated offset\n const leftCursorWordLength = offset - wordStart;\n const rightCursorWordLength = wordEnd - offset;\n let movingOffset: number =\n leftCursorWordLength >= rightCursorWordLength\n ? rightCursorWordLength\n : -leftCursorWordLength;\n movingOffset =\n Math.abs(movingOffset) > MAX_TOUCH_MOVE_DISTANCE\n ? 0\n : movingOffset;\n const newOffsetPosition = offset + movingOffset;\n if (\n movingOffset !== 0 &&\n nodeTextContent.length >= newOffsetPosition\n ) {\n newRange.setStart(node, newOffsetPosition);\n newRange.setEnd(node, newOffsetPosition);\n }\n }\n }\n this.editor.setDOMSelection({\n type: 'range',\n range: newRange,\n isReverted: false,\n });\n\n // reset values\n this.isTouchPenPointerEvent = false;\n }\n }\n }, POINTER_DETECTION_DELAY);\n }\n break;\n case 'doubleClick':\n if (this.isTouchPenPointerEvent) {\n event.rawEvent.preventDefault();\n\n this.isDblClicked = true;\n const caretPosition = getNodePositionFromEvent(\n this.editor.getDocument(),\n this.editor.getDOMHelper(),\n event.rawEvent.x,\n event.rawEvent.y\n );\n\n if (caretPosition) {\n const { node, offset } = caretPosition;\n\n if (node.nodeType !== Node.TEXT_NODE) {\n return;\n }\n\n const nodeTextContent = node.nodeValue || '';\n const char = nodeTextContent.charAt(offset);\n\n // Check if the clicked character is a punctuation mark, then highlight that character only\n if (PUNCTUATION_MATCHING_REGEX.test(char)) {\n const newRange = this.editor.getDocument()?.createRange();\n if (newRange) {\n newRange.setStart(node, offset);\n newRange.setEnd(node, offset + 1);\n this.editor.setDOMSelection({\n type: 'range',\n range: newRange,\n isReverted: false,\n });\n }\n } else if (SPACE_MATCHING_REGEX.test(char)) {\n // If the clicked character is an open space with no word of right side\n const rightSideOfChar = nodeTextContent.substring(\n offset,\n nodeTextContent.length\n );\n const isRightSideAllSpaces =\n rightSideOfChar.length > 0 && !/\\S/.test(rightSideOfChar);\n if (isRightSideAllSpaces) {\n // select the first space only\n let start = offset;\n while (\n start > 0 &&\n SPACE_MATCHING_REGEX.test(nodeTextContent.charAt(start - 1))\n ) {\n start--;\n }\n const newRange = this.editor.getDocument()?.createRange();\n if (newRange) {\n newRange.setStart(node, start);\n newRange.setEnd(node, start + 1);\n this.editor.setDOMSelection({\n type: 'range',\n range: newRange,\n isReverted: false,\n });\n }\n }\n } else {\n const { wordStart, wordEnd } = findWordBoundaries(\n nodeTextContent,\n offset\n );\n const newRange = this.editor.getDocument()?.createRange();\n if (newRange) {\n newRange.setStart(node, wordStart);\n newRange.setEnd(node, wordEnd);\n this.editor.setDOMSelection({\n type: 'range',\n range: newRange,\n isReverted: false,\n });\n }\n }\n }\n }\n break;\n }\n }\n}\n\n/**\n * @internal\n * Finds the start and end indices of the word at the given offset in the text.\n * @param text The string to search within.\n * @param offset The index within the string to find the word boundaries around.\n * @returns An object containing wordStart and wordEnd indices.\n */\nfunction findWordBoundaries(text: string, offset: number) {\n let start = offset;\n let end = offset;\n\n // Move start backwards to find word start\n while (\n start > 0 &&\n !SPACE_MATCHING_REGEX.test(text[start - 1]) &&\n !PUNCTUATION_MATCHING_REGEX.test(text[start - 1])\n ) {\n start--;\n }\n\n // Move end forward to find word end\n while (\n end < text.length &&\n !SPACE_MATCHING_REGEX.test(text[end]) &&\n !PUNCTUATION_MATCHING_REGEX.test(text[end])\n ) {\n end++;\n }\n\n return {\n wordStart: start,\n wordEnd: end,\n };\n}\n"]}
|
|
@@ -455,7 +455,7 @@ var ImageEditPlugin = /** @class */ (function () {
|
|
|
455
455
|
operation === 'crop');
|
|
456
456
|
};
|
|
457
457
|
ImageEditPlugin.prototype.canRegenerateImage = function (image) {
|
|
458
|
-
return canRegenerateImage(image);
|
|
458
|
+
return canRegenerateImage(image, this.options.resolveImageSource);
|
|
459
459
|
};
|
|
460
460
|
ImageEditPlugin.prototype.startCropMode = function (editor, image, isRTL) {
|
|
461
461
|
var _this = this;
|