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 | 1x 1x 21x 21x 21x 21x 20x 20x 20x 20x 20x 20x 20x 20x 1x 22x 22x 22x 22x 22x 22x 5x 5x 5x 13x 13x 13x | import { addBlock, mutateBlock, setParagraphNotImplicit } from 'roosterjs-content-model-dom';
import type {
ContentModelBlock,
ContentModelBlockGroup,
ReadonlyContentModelBlock,
ReadonlyContentModelBlockGroup,
ShallowMutableContentModelBlock,
} from 'roosterjs-content-model-types';
/**
* @internal
*/
export interface WrapBlockStep1Result<T extends ContentModelBlockGroup & ContentModelBlock> {
parent: ReadonlyContentModelBlockGroup;
wrapper: T;
}
/**
* @internal
*/
export function wrapBlockStep1<T extends ContentModelBlockGroup & ContentModelBlock>(
step1Result: WrapBlockStep1Result<T>[],
readonlyParent: ReadonlyContentModelBlockGroup | null,
readonlyBlockToWrap: ReadonlyContentModelBlock,
creator: (isRtl: boolean) => T,
canMerge: (isRtl: boolean, target: ShallowMutableContentModelBlock) => target is T
) {
const parent = readonlyParent ? mutateBlock(readonlyParent) : null;
const blockToWrap = mutateBlock(readonlyBlockToWrap);
const index = parent?.blocks.indexOf(blockToWrap) ?? -1;
if (parent && index >= 0) {
parent.blocks.splice(index, 1);
const readonlyPrevBlock: ReadonlyContentModelBlock = parent.blocks[index - 1];
const prevBlock = readonlyPrevBlock ? mutateBlock(readonlyPrevBlock) : null;
const isRtl = blockToWrap.format.direction == 'rtl';
const wrapper =
prevBlock && canMerge(isRtl, prevBlock)
? prevBlock
: createAndAdd(parent, index, creator, isRtl);
setParagraphNotImplicit(blockToWrap);
addBlock(wrapper, blockToWrap);
// Use reverse order, so that we can merge from last to first to avoid modifying unmerged quotes
step1Result.unshift({ parent, wrapper });
}
}
/**
* @internal
*/
export function wrapBlockStep2<T extends ContentModelBlockGroup & ContentModelBlock>(
step1Result: WrapBlockStep1Result<T>[],
canMerge: (isRtl: boolean, target: ShallowMutableContentModelBlock, current: T) => target is T
) {
step1Result.forEach(({ parent, wrapper }) => {
const index = parent.blocks.indexOf(wrapper);
const readonlyNextBlock = parent.blocks[index + 1];
const nextBlock = readonlyNextBlock ? mutateBlock(readonlyNextBlock) : null;
const isRtl = wrapper.format.direction == 'rtl';
if (index >= 0 && nextBlock && canMerge(isRtl, nextBlock, wrapper)) {
wrapper.blocks.forEach(setParagraphNotImplicit);
wrapper.blocks.push(...nextBlock.blocks);
mutateBlock(parent).blocks.splice(index + 1, 1);
}
});
}
function createAndAdd<T extends ContentModelBlockGroup & ContentModelBlock>(
parent: ReadonlyContentModelBlockGroup,
index: number,
creator: (isRtl: boolean) => T,
isRtl: boolean
): T {
const block = creator(isRtl);
mutateBlock(parent).blocks.splice(index, 0, block);
return block;
}
|