Press n or j to go to the next uncovered block, b, p or k for the previous block.
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 | 1x 1x 5x 1x 4x 4x 4x 4x 4x 4x 4x 8x 8x 3x 3x 3x 5x 1x 4x 4x 4x 4x 4x 4x 4x 8x 8x 8x | import { getObjectKeys, isNodeOfType } from 'roosterjs-content-model-dom';
/**
* @internal
*/
export function replaceTextInRange(
range: Range,
replaceText: string,
foundRanges: Range[]
): Range | null {
if (
!isNodeOfType(range.startContainer, 'TEXT_NODE') ||
!isNodeOfType(range.endContainer, 'TEXT_NODE')
) {
return null;
}
const textNode = range.startContainer;
const resultContainer = range.startContainer;
const resultOffset = range.startOffset + replaceText.length;
const originalText = textNode.textContent || '';
const newText =
originalText.substring(0, range.startOffset) +
replaceText +
(range.endContainer == range.startContainer
? originalText.substring(range.endOffset, textNode.textContent?.length)
: '');
const pendingRanges: Record<
number,
{
startContainer: Node;
startOffset: number;
endContainer: Node;
endOffset: number;
}
> = {};
for (let i = 0; i < foundRanges.length; i++) {
const r = foundRanges[i];
if (r.startContainer == range.endContainer && r.startOffset >= range.endOffset) {
const startOffset =
range.startContainer == range.endContainer
? r.startOffset - range.endOffset + range.startOffset + replaceText.length
: r.startOffset - range.endOffset;
const endOffset =
r.startContainer == r.endContainer
? startOffset + (r.endOffset - r.startOffset)
: r.endOffset;
pendingRanges[i] = {
startContainer: r.startContainer,
endContainer: r.endContainer,
startOffset,
endOffset,
};
} else if (r.endContainer == range.startContainer && r.endOffset <= range.startOffset) {
pendingRanges[i] = {
startContainer: r.startContainer,
endContainer: r.endContainer,
startOffset: r.startOffset,
endOffset: r.endOffset,
};
}
}
range.deleteContents();
textNode.nodeValue = newText;
getObjectKeys(pendingRanges).forEach(i => {
const { startOffset, endOffset, startContainer, endContainer } = pendingRanges[i];
safeSetRange(foundRanges[i], startContainer, startOffset, endContainer, endOffset);
});
safeSetRange(range, resultContainer, resultOffset, resultContainer, resultOffset);
return range;
}
function safeSetRange(
range: Range,
startContainer: Node,
startOffset: number,
endContainer: Node,
endOffset: number
) {
Eif (
isNodeOfType(startContainer, 'TEXT_NODE') &&
isNodeOfType(endContainer, 'TEXT_NODE') &&
startOffset >= 0 &&
startOffset <= (startContainer.nodeValue?.length ?? 0) &&
endOffset >= 0 &&
endOffset <= (endContainer.nodeValue?.length ?? 0)
) {
range.setStart(startContainer, startOffset);
range.setEnd(endContainer, endOffset);
}
}
|