@docx4j/core-ts 0.5.0 → 0.7.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/NOTICE +4 -0
- package/README.md +92 -4
- package/dist/html/convert.mjs +2 -1
- package/dist/html/elements.mjs +2 -1
- package/dist/model/color/ColorMath.d.mts +29 -0
- package/dist/model/color/ColorMath.mjs +146 -0
- package/dist/model/color/ColorTables.d.mts +6 -0
- package/dist/model/color/ColorTables.mjs +83 -0
- package/dist/model/color/DrawingMLColors.d.mts +52 -0
- package/dist/model/color/DrawingMLColors.mjs +374 -0
- package/dist/model/color/ResolvedColor.d.mts +36 -0
- package/dist/model/color/ResolvedColor.mjs +65 -0
- package/dist/model/color/SpreadsheetColors.d.mts +36 -0
- package/dist/model/color/SpreadsheetColors.mjs +84 -0
- package/dist/model/color/StyleFill.d.mts +28 -0
- package/dist/model/color/StyleFill.mjs +21 -0
- package/dist/model/color/ThemeColors.d.mts +86 -0
- package/dist/model/color/ThemeColors.mjs +304 -0
- package/dist/model/color/WordColors.d.mts +71 -0
- package/dist/model/color/WordColors.mjs +121 -0
- package/dist/model/color/index.d.mts +6 -0
- package/dist/model/color/index.mjs +30 -0
- package/dist/model/content/Body.d.mts +145 -23
- package/dist/model/content/Body.mjs +507 -150
- package/dist/model/content/Comment.d.mts +23 -5
- package/dist/model/content/Comment.mjs +207 -26
- package/dist/model/content/ContentControl.d.mts +198 -19
- package/dist/model/content/ContentControl.mjs +672 -99
- package/dist/model/content/Font.d.mts +70 -17
- package/dist/model/content/Font.mjs +119 -36
- package/dist/model/content/InlinePicture.d.mts +11 -0
- package/dist/model/content/InlinePicture.mjs +21 -1
- package/dist/model/content/List.d.mts +6 -3
- package/dist/model/content/List.mjs +18 -8
- package/dist/model/content/Paragraph.d.mts +200 -14
- package/dist/model/content/Paragraph.mjs +898 -82
- package/dist/model/content/Range.d.mts +227 -12
- package/dist/model/content/Range.mjs +785 -59
- package/dist/model/content/ResolvedView.d.mts +104 -0
- package/dist/model/content/ResolvedView.mjs +596 -0
- package/dist/model/content/Table.d.mts +29 -3
- package/dist/model/content/Table.mjs +135 -49
- package/dist/model/content/TrackedChange.d.mts +174 -15
- package/dist/model/content/TrackedChange.mjs +734 -170
- package/dist/model/content/comments.d.mts +20 -6
- package/dist/model/content/comments.mjs +67 -57
- package/dist/model/content/generalException.d.mts +18 -0
- package/dist/model/content/generalException.mjs +24 -0
- package/dist/model/content/index.d.mts +10 -3
- package/dist/model/content/index.mjs +10 -2
- package/dist/model/content/mathText.d.mts +21 -0
- package/dist/model/content/mathText.mjs +267 -0
- package/dist/model/content/officeText.d.mts +27 -0
- package/dist/model/content/officeText.mjs +74 -0
- package/dist/model/content/ooxml.mjs +12 -1
- package/dist/model/content/outline.d.mts +5 -0
- package/dist/model/content/outline.mjs +13 -0
- package/dist/model/content/paraIds.d.mts +5 -0
- package/dist/model/content/paraIds.mjs +54 -0
- package/dist/model/content/placeholders.d.mts +110 -0
- package/dist/model/content/placeholders.mjs +253 -0
- package/dist/model/content/search.d.mts +74 -0
- package/dist/model/content/search.mjs +255 -9
- package/dist/model/content/spanEdits.d.mts +159 -0
- package/dist/model/content/spanEdits.mjs +728 -0
- package/dist/model/content/story.d.mts +47 -0
- package/dist/model/content/story.mjs +95 -0
- package/dist/model/content/tableColumns.d.mts +1 -1
- package/dist/model/content/tableColumns.mjs +108 -80
- package/dist/model/content/tableRevisions.d.mts +11 -3
- package/dist/model/content/tableRevisions.mjs +72 -42
- package/dist/model/content/tableRules.d.mts +30 -0
- package/dist/model/content/tableRules.mjs +102 -0
- package/dist/model/content/textBoxes.d.mts +18 -0
- package/dist/model/content/textBoxes.mjs +105 -0
- package/dist/model/content/trackedChangeFilter.d.mts +39 -0
- package/dist/model/content/trackedChangeFilter.mjs +81 -0
- package/dist/model/content/tracking.d.mts +63 -6
- package/dist/model/content/tracking.mjs +242 -22
- package/dist/model/content/tree.d.mts +172 -24
- package/dist/model/content/tree.mjs +328 -54
- package/dist/model/content/wordRange.d.mts +48 -0
- package/dist/model/content/wordRange.mjs +97 -0
- package/dist/model/customxml/CustomXmlPartCollection.d.mts +30 -1
- package/dist/model/customxml/CustomXmlPartCollection.mjs +81 -12
- package/dist/model/customxml/XmlMapping.d.mts +32 -8
- package/dist/model/customxml/XmlMapping.mjs +64 -10
- package/dist/model/customxml/bindings.d.mts +33 -4
- package/dist/model/customxml/bindings.mjs +171 -45
- package/dist/model/customxml/index.d.mts +1 -0
- package/dist/model/customxml/index.mjs +1 -0
- package/dist/model/customxml/kinds.d.mts +8 -3
- package/dist/model/customxml/kinds.mjs +26 -5
- package/dist/model/customxml/opendope.d.mts +4 -1
- package/dist/model/customxml/opendope.mjs +9 -6
- package/dist/model/customxml/picturePlaceholder.d.mts +17 -0
- package/dist/model/customxml/picturePlaceholder.mjs +32 -0
- package/dist/model/customxml/pictures.d.mts +4 -3
- package/dist/model/customxml/pictures.mjs +22 -8
- package/dist/model/customxml/storeItems.d.mts +57 -0
- package/dist/model/customxml/storeItems.mjs +122 -0
- package/dist/model/customxml/xhtml.mjs +23 -22
- package/dist/model/dateZone.d.mts +25 -0
- package/dist/model/dateZone.mjs +57 -0
- package/dist/model/index.d.mts +3 -0
- package/dist/model/index.mjs +5 -0
- package/dist/model/listnumbering/Emulator.d.mts +37 -5
- package/dist/model/listnumbering/Emulator.mjs +63 -9
- package/dist/model/properties/PropertyResolver.d.mts +74 -2
- package/dist/model/properties/PropertyResolver.mjs +133 -5
- package/dist/model/properties/catalogue.d.mts +19 -5
- package/dist/model/properties/catalogue.mjs +41 -15
- package/dist/model/properties/index.d.mts +1 -1
- package/dist/model/properties/log.d.mts +1 -1
- package/dist/model/properties/log.mjs +5 -5
- package/dist/model/properties/styleUtil.d.mts +3 -1
- package/dist/model/properties/styleUtil.mjs +20 -24
- package/dist/model/properties/table.mjs +4 -2
- package/dist/model/text/CaseMapping.d.mts +38 -0
- package/dist/model/text/CaseMapping.mjs +86 -0
- package/dist/model/text/Extractor.d.mts +349 -0
- package/dist/model/text/Extractor.mjs +2406 -0
- package/dist/model/text/LinkTargets.d.mts +45 -0
- package/dist/model/text/LinkTargets.mjs +170 -0
- package/dist/model/text/MarkdownExporter.d.mts +140 -0
- package/dist/model/text/MarkdownExporter.mjs +255 -0
- package/dist/model/text/PlainText.d.mts +29 -0
- package/dist/model/text/PlainText.mjs +542 -0
- package/dist/model/text/TextContext.d.mts +256 -0
- package/dist/model/text/TextContext.mjs +600 -0
- package/dist/model/text/TextOptions.d.mts +233 -0
- package/dist/model/text/TextOptions.mjs +419 -0
- package/dist/model/text/TextResult.d.mts +621 -0
- package/dist/model/text/TextResult.mjs +629 -0
- package/dist/model/text/Texts.d.mts +99 -0
- package/dist/model/text/Texts.mjs +187 -0
- package/dist/model/text/WmlToMarkdown.d.mts +120 -0
- package/dist/model/text/WmlToMarkdown.mjs +936 -0
- package/dist/model/text/caseMapping.generated.d.mts +7 -0
- package/dist/model/text/caseMapping.generated.mjs +214 -0
- package/dist/model/text/commonmark.d.mts +121 -0
- package/dist/model/text/commonmark.mjs +655 -0
- package/dist/model/text/index.d.mts +8 -0
- package/dist/model/text/index.mjs +9 -0
- package/dist/model/text/normalize.d.mts +8 -0
- package/dist/model/text/normalize.mjs +13 -0
- package/dist/model/text/outline.d.mts +4 -0
- package/dist/model/text/outline.mjs +71 -0
- package/dist/model/wordIntegers.d.mts +29 -0
- package/dist/model/wordIntegers.mjs +78 -0
- package/dist/office-js/document.mjs +15 -1
- package/dist/office-js/fragment.d.mts +7 -5
- package/dist/office-js/fragment.mjs +63 -14
- package/dist/office-js/proxy.d.mts +8 -0
- package/dist/office-js/proxy.mjs +29 -0
- package/dist/office-js/run.mjs +2 -0
- package/dist/office-js/supported.generated.mjs +16 -0
- package/dist/office-js/toApiScript.mjs +29 -12
- package/dist/opc/DirectoryPartStore.d.mts +6 -2
- package/dist/opc/DirectoryPartStore.mjs +11 -4
- package/dist/opc/FlatOpcPartStore.d.mts +4 -2
- package/dist/opc/FlatOpcPartStore.mjs +11 -8
- package/dist/opc/Load.d.mts +32 -0
- package/dist/opc/Load.mjs +115 -5
- package/dist/opc/PartStore.d.mts +34 -1
- package/dist/opc/PartStore.mjs +71 -8
- package/dist/opc/Save.d.mts +32 -0
- package/dist/opc/Save.mjs +110 -4
- package/dist/opc/ZipPartStore.d.mts +4 -2
- package/dist/opc/ZipPartStore.mjs +12 -7
- package/dist/opc/exceptions.d.mts +140 -0
- package/dist/opc/exceptions.mjs +108 -0
- package/dist/opc/index.d.mts +8 -5
- package/dist/opc/index.mjs +5 -3
- package/dist/opc/mce/preprocessor.d.mts +141 -5
- package/dist/opc/mce/preprocessor.mjs +119 -18
- package/dist/opc/mce/understood.d.mts +3 -11
- package/dist/opc/mce/understood.mjs +27 -23
- package/dist/opc/repair/breaks.d.mts +23 -0
- package/dist/opc/repair/breaks.mjs +288 -0
- package/dist/opc/repair/hosts.d.mts +12 -0
- package/dist/opc/repair/hosts.mjs +33 -0
- package/dist/opc/repair/mainRoot.d.mts +19 -0
- package/dist/opc/repair/mainRoot.mjs +168 -0
- package/dist/opc/repair/unknownElements.d.mts +8 -0
- package/dist/opc/repair/unknownElements.mjs +180 -0
- package/dist/opc/repair/wmlNames.generated.d.mts +2 -0
- package/dist/opc/repair/wmlNames.generated.mjs +80 -0
- package/dist/opc/skipped.d.mts +50 -0
- package/dist/opc/skipped.mjs +140 -0
- package/dist/packages/OpcPackage.d.mts +110 -4
- package/dist/packages/OpcPackage.mjs +123 -7
- package/dist/packages/WordprocessingMLPackage.d.mts +45 -8
- package/dist/packages/WordprocessingMLPackage.mjs +158 -21
- package/dist/packages/index.d.mts +1 -1
- package/dist/parts/DefaultXmlPart.mjs +2 -2
- package/dist/parts/Part.d.mts +14 -2
- package/dist/parts/RelationshipsPart.d.mts +15 -0
- package/dist/parts/RelationshipsPart.mjs +66 -1
- package/dist/parts/XmlPart.d.mts +63 -32
- package/dist/parts/XmlPart.mjs +240 -96
- package/dist/parts/wml/comments.mjs +30 -0
- package/dist/parts/wml/index.d.mts +12 -1
- package/dist/parts/wml/index.mjs +37 -1
- package/dist/xml/dom.d.mts +7 -0
- package/dist/xml/dom.mjs +18 -0
- package/package.json +2 -2
|
@@ -0,0 +1,596 @@
|
|
|
1
|
+
import { typeNameOf, runItemsOf, childrenOf, revisionKindOf, itemTextOf } from './tree.mjs';
|
|
2
|
+
import { movePiecesOf, storyOf, firstCellParagraphOf } from './TrackedChange.mjs';
|
|
3
|
+
import { trackedChangesOfStory } from './Body.mjs';
|
|
4
|
+
import { HOLDER_TYPES } from './tracking.mjs';
|
|
5
|
+
const valueOf = (item) => (typeof item === 'object' && item !== null && 'value' in item && 'name' in item ? item.value : item);
|
|
6
|
+
const localName = (item) => { var _a, _b; return (typeof item === 'object' && item !== null && 'name' in item ? (_b = (_a = item.name) === null || _a === void 0 ? void 0 : _a.localPart) !== null && _b !== void 0 ? _b : '' : ''); };
|
|
7
|
+
const commentIdOf = (item) => { var _a; return (_a = valueOf(item)) === null || _a === void 0 ? void 0 : _a.id; };
|
|
8
|
+
/** The index in `list`, from `from` up to `to`, of a comment's range start or end (`local`), or -1. */
|
|
9
|
+
function markerAt(list, from, to, local, id) {
|
|
10
|
+
for (let i = from; i < to; i++)
|
|
11
|
+
if (localName(list[i]) === local && commentIdOf(list[i]) === id)
|
|
12
|
+
return i;
|
|
13
|
+
return -1;
|
|
14
|
+
}
|
|
15
|
+
/** A block-level control's content, which holds paragraphs. */
|
|
16
|
+
const SDT_CONTENTS = new Set(['org_docx4j_wml.SdtContentBlock', 'org_docx4j_wml.CTSdtContentBlock']);
|
|
17
|
+
/** A marker that stands between two blocks without keeping them apart, as a join reads one. */
|
|
18
|
+
function isRangeMarker(item) {
|
|
19
|
+
const name = localName(item);
|
|
20
|
+
return name.endsWith('RangeStart') || name.endsWith('RangeEnd') || name === 'bookmarkStart' || name === 'bookmarkEnd'
|
|
21
|
+
|| name === 'permStart' || name === 'permEnd' || name === 'proofErr';
|
|
22
|
+
}
|
|
23
|
+
/** The live list of run-level content a holder keeps, or of block content a container keeps. */
|
|
24
|
+
function listOf(value) {
|
|
25
|
+
var _a;
|
|
26
|
+
if (typeof value !== 'object' || value === null)
|
|
27
|
+
return undefined;
|
|
28
|
+
return (_a = runItemsOf(value)) !== null && _a !== void 0 ? _a : childrenOf(value);
|
|
29
|
+
}
|
|
30
|
+
/**
|
|
31
|
+
* What Word's Accept All or Reject All would leave of a document, as `acceptAllRevisions` and
|
|
32
|
+
* `rejectAllRevisions` leave it, worked out without resolving anything: the content each removes and the
|
|
33
|
+
* paragraphs each joins. A reader walks the unresolved tree and asks this view what is there, so that the
|
|
34
|
+
* text it reads in a view is the text of the resolved document (WD REQ-402), and the package is untouched
|
|
35
|
+
* (REQ-204). docx4j `org.docx4j.model.revisions.ResolvedView`.
|
|
36
|
+
*
|
|
37
|
+
* It lists each story's changes (`trackedChangesOfStory`, text boxes in their selected branch) and
|
|
38
|
+
* records, change by change, what the resolution would do to the text: a revision taken away, a move's
|
|
39
|
+
* halves and the text typed into a rejected move's destination, an inserted field rejected whole, a row
|
|
40
|
+
* or cell taken away, an equation's run-level revision or structure, a paragraph mark taken away, and an
|
|
41
|
+
* inserted content control rejected (its content left in its place). What a resolution does to
|
|
42
|
+
* properties, range markers, comments' entries and parts is not recorded; the comments a resolution takes
|
|
43
|
+
* whole are (CR-002 section 54).
|
|
44
|
+
*
|
|
45
|
+
* A snapshot over the trees it was made from: valid until they change.
|
|
46
|
+
*/
|
|
47
|
+
export class ResolvedView {
|
|
48
|
+
constructor(stories, accepted) {
|
|
49
|
+
this.accepted = accepted;
|
|
50
|
+
/** List members gone, by identity of their values. */
|
|
51
|
+
this.removed = new Set();
|
|
52
|
+
/** Content controls and custom XML elements gone, their content standing in their place. */
|
|
53
|
+
this.unwrapped = new Set();
|
|
54
|
+
/** Paragraphs whose mark is gone. */
|
|
55
|
+
this.marksGone = new Set();
|
|
56
|
+
/** Moved paragraphs whose mark is gone: gone themselves when nothing is left in them, else joined. */
|
|
57
|
+
this.movedMarksGone = new Set();
|
|
58
|
+
this.commentCandidates = [];
|
|
59
|
+
this.spanCandidates = [];
|
|
60
|
+
this.commentsGone = new Set();
|
|
61
|
+
/** Move halves whose story has no piece for them (a text box's, whose paragraphs' story is the body around it). */
|
|
62
|
+
this.unreplayed = new Set();
|
|
63
|
+
const changes = [];
|
|
64
|
+
for (const body of stories)
|
|
65
|
+
changes.push(...trackedChangesOfStory(body));
|
|
66
|
+
// moves first, story by story, in the resolution's order: their outcome depends on it
|
|
67
|
+
const moves = new Map();
|
|
68
|
+
for (const change of changes)
|
|
69
|
+
this.collectMoves(change, moves);
|
|
70
|
+
for (const [story, halves] of moves)
|
|
71
|
+
for (const missing of new MoveReplay(this, story, halves).run())
|
|
72
|
+
this.unreplayed.add(missing);
|
|
73
|
+
for (const change of changes)
|
|
74
|
+
this.plan(change);
|
|
75
|
+
for (const c of this.commentCandidates)
|
|
76
|
+
if (c.rangeEmpty())
|
|
77
|
+
this.commentsGone.add(Number(c.id));
|
|
78
|
+
for (const c of this.spanCandidates)
|
|
79
|
+
if (c.rangeEmpty())
|
|
80
|
+
this.commentsGone.add(Number(c.id));
|
|
81
|
+
}
|
|
82
|
+
/** The document after Accept All, over these stories (each a `Body` over the tree a reader walks). */
|
|
83
|
+
static accepted(stories) {
|
|
84
|
+
return new ResolvedView(stories, true);
|
|
85
|
+
}
|
|
86
|
+
/** The document after Reject All. */
|
|
87
|
+
static original(stories) {
|
|
88
|
+
return new ResolvedView(stories, false);
|
|
89
|
+
}
|
|
90
|
+
collectMoves(change, moves) {
|
|
91
|
+
const t = change.target;
|
|
92
|
+
if (t.kind === 'group') {
|
|
93
|
+
for (const piece of t.pieces)
|
|
94
|
+
this.collectMoves(piece, moves);
|
|
95
|
+
return;
|
|
96
|
+
}
|
|
97
|
+
if (t.kind === 'row') {
|
|
98
|
+
for (const inner of t.inner)
|
|
99
|
+
this.collectMoves(inner, moves);
|
|
100
|
+
return;
|
|
101
|
+
}
|
|
102
|
+
if (t.kind !== 'run' || (t.revision !== 'moveFrom' && t.revision !== 'moveTo') || !change.paragraph)
|
|
103
|
+
return;
|
|
104
|
+
const story = storyOf(change.paragraph.p);
|
|
105
|
+
let list = moves.get(story);
|
|
106
|
+
if (!list)
|
|
107
|
+
moves.set(story, (list = []));
|
|
108
|
+
list.push(change);
|
|
109
|
+
}
|
|
110
|
+
/**
|
|
111
|
+
* Whether a list member is gone in this view: a run-level revision taken away with its content, a run,
|
|
112
|
+
* a row, a cell, a paragraph, an equation's run-level revision or structure. A revision that is not
|
|
113
|
+
* gone is kept: its content is read as if it were not there. An element pair and its value alike.
|
|
114
|
+
*/
|
|
115
|
+
removes(item) {
|
|
116
|
+
var _a;
|
|
117
|
+
const v = valueOf(item);
|
|
118
|
+
if (v === undefined || v === null)
|
|
119
|
+
return false;
|
|
120
|
+
if (this.removed.has(v))
|
|
121
|
+
return true;
|
|
122
|
+
const tn = typeNameOf(v);
|
|
123
|
+
if (tn === 'org_docx4j_wml.Tbl')
|
|
124
|
+
return this.emptiedTable(v);
|
|
125
|
+
if (tn !== 'org_docx4j_wml.P')
|
|
126
|
+
return false;
|
|
127
|
+
const p = v;
|
|
128
|
+
if (this.movedMarksGone.has(p) && !this.remainsIn(p))
|
|
129
|
+
return true;
|
|
130
|
+
if (!this.marksGone.has(p))
|
|
131
|
+
return false;
|
|
132
|
+
// an emptied paragraph whose mark is gone, with a table or a block control next in its list: gone (docx4j CR-043
|
|
133
|
+
// section 17: check 54 case 9, the text-left probe's case 3). One with text left and a table next isn't removed but
|
|
134
|
+
// moved: `joinsIntoTable`, which the walk applies
|
|
135
|
+
const next = this.nextBlockAfter(p);
|
|
136
|
+
return !this.remainsIn(p) && (typeNameOf(next) === 'org_docx4j_wml.Tbl' || HOLDER_TYPES.has((_a = typeNameOf(next)) !== null && _a !== void 0 ? _a : ''));
|
|
137
|
+
}
|
|
138
|
+
/**
|
|
139
|
+
* The table a paragraph with text left joins into, where its mark is gone and a table is the next block in its list
|
|
140
|
+
* (Word 365's Accept All, docx4j CR-043 section 17, the text-left probe's case 1: its content lands at the front of the
|
|
141
|
+
* first cell's first paragraph, which keeps its own properties); undefined otherwise. docx4j `joinsIntoTable`.
|
|
142
|
+
*/
|
|
143
|
+
joinsIntoTable(p) {
|
|
144
|
+
if (!this.marksGone.has(p) || !this.remainsIn(p))
|
|
145
|
+
return undefined;
|
|
146
|
+
const next = this.nextBlockAfter(p);
|
|
147
|
+
return typeNameOf(next) === 'org_docx4j_wml.Tbl' && firstCellParagraphOf(next) ? next : undefined;
|
|
148
|
+
}
|
|
149
|
+
/**
|
|
150
|
+
* A paragraph's properties in this view, where its mark is gone and no paragraph follows it in its list (Word 365's
|
|
151
|
+
* Accept All, check 54; docx4j CR-043 section 17): a block control next gives it the control's first paragraph's
|
|
152
|
+
* properties, as a join would have (case 19); a control's last paragraph keeps a bare mark, its properties gone, its
|
|
153
|
+
* text left or not (case 13, the text-left probe's case 2); otherwise its own. docx4j `paragraphPropertiesOf`.
|
|
154
|
+
*/
|
|
155
|
+
paragraphPropertiesOf(p) {
|
|
156
|
+
var _a, _b, _c;
|
|
157
|
+
if (!this.marksGone.has(p))
|
|
158
|
+
return p.pPr;
|
|
159
|
+
const parent = p.PARENT;
|
|
160
|
+
const container = listOf(parent);
|
|
161
|
+
const k = container ? container.findIndex((item) => valueOf(item) === p) : -1;
|
|
162
|
+
if (!container || k < 0)
|
|
163
|
+
return p.pPr;
|
|
164
|
+
const next = this.nextBlock(container, k);
|
|
165
|
+
if (typeNameOf(next) === 'org_docx4j_wml.P')
|
|
166
|
+
return p.pPr; // a join: the walk takes the chain's last
|
|
167
|
+
if (next && HOLDER_TYPES.has((_a = typeNameOf(next)) !== null && _a !== void 0 ? _a : '')) {
|
|
168
|
+
for (const o of (_b = childrenOf(next)) !== null && _b !== void 0 ? _b : []) {
|
|
169
|
+
if (typeNameOf(o) === 'org_docx4j_wml.P')
|
|
170
|
+
return o.value.pPr;
|
|
171
|
+
if (typeNameOf(o) === 'org_docx4j_wml.Tbl')
|
|
172
|
+
break;
|
|
173
|
+
}
|
|
174
|
+
}
|
|
175
|
+
if (next === undefined && SDT_CONTENTS.has((_c = parent === null || parent === void 0 ? void 0 : parent.TYPE_NAME) !== null && _c !== void 0 ? _c : ''))
|
|
176
|
+
return undefined; // a bare mark, text or not (the probe's case 2)
|
|
177
|
+
return p.pPr;
|
|
178
|
+
}
|
|
179
|
+
/**
|
|
180
|
+
* A table whose every row this view removes is gone with them, as the resolution removes an emptied table
|
|
181
|
+
* (check 54 case 6: a deletion from a heading across a whole table joins the heading with the paragraph after it).
|
|
182
|
+
*/
|
|
183
|
+
emptiedTable(tbl) {
|
|
184
|
+
var _a;
|
|
185
|
+
let rows = false;
|
|
186
|
+
for (const item of ((_a = tbl.content) !== null && _a !== void 0 ? _a : [])) {
|
|
187
|
+
if (typeNameOf(item) === 'org_docx4j_wml.Tr') {
|
|
188
|
+
rows = true;
|
|
189
|
+
if (!this.removed.has(item.value))
|
|
190
|
+
return false;
|
|
191
|
+
}
|
|
192
|
+
else if (!isRangeMarker(item))
|
|
193
|
+
return false;
|
|
194
|
+
}
|
|
195
|
+
return rows;
|
|
196
|
+
}
|
|
197
|
+
/** The block after `p` in its list, past range markers and what this view removes; undefined at the end. */
|
|
198
|
+
nextBlockAfter(p) {
|
|
199
|
+
const container = listOf(p.PARENT);
|
|
200
|
+
const k = container ? container.findIndex((item) => valueOf(item) === p) : -1;
|
|
201
|
+
return container && k >= 0 ? this.nextBlock(container, k) : undefined;
|
|
202
|
+
}
|
|
203
|
+
nextBlock(container, k) {
|
|
204
|
+
for (let i = k + 1; i < container.length; i++) {
|
|
205
|
+
const item = container[i];
|
|
206
|
+
if (isRangeMarker(item) || this.removes(item))
|
|
207
|
+
continue;
|
|
208
|
+
return valueOf(item);
|
|
209
|
+
}
|
|
210
|
+
return undefined;
|
|
211
|
+
}
|
|
212
|
+
/** Whether a content control or custom XML element is gone with its content left in its place (one inserted, rejected). */
|
|
213
|
+
unwraps(item) {
|
|
214
|
+
const v = valueOf(item);
|
|
215
|
+
return v !== undefined && v !== null && this.unwrapped.has(v);
|
|
216
|
+
}
|
|
217
|
+
/**
|
|
218
|
+
* Whether a paragraph's mark is gone in this view: a deletion accepted, an insertion rejected, a move's
|
|
219
|
+
* mark on the side not kept. Such a paragraph joins the next one in its list, past range markers and
|
|
220
|
+
* what this view removes, when that is a paragraph; with no paragraph next only the mark goes.
|
|
221
|
+
*/
|
|
222
|
+
removesMark(p) {
|
|
223
|
+
return p !== undefined && (this.marksGone.has(p) || this.movedMarksGone.has(p));
|
|
224
|
+
}
|
|
225
|
+
/**
|
|
226
|
+
* Whether a comment goes in this view, entry and reference: one whose range started on a revision taken
|
|
227
|
+
* away, or whose markers lie either side of one, once nothing with text is left in its range (CR-002
|
|
228
|
+
* section 54).
|
|
229
|
+
*/
|
|
230
|
+
removesComment(id) {
|
|
231
|
+
return id !== undefined && id !== null && this.commentsGone.has(Number(id));
|
|
232
|
+
}
|
|
233
|
+
// --- the plan, change by change, as the resolution resolves each ----------------------------
|
|
234
|
+
plan(change) {
|
|
235
|
+
const t = change.target;
|
|
236
|
+
switch (t.kind) {
|
|
237
|
+
case 'run': {
|
|
238
|
+
// a move is replayed, unless its story has no piece for it (a text box's, whose paragraphs' story is
|
|
239
|
+
// the body around it): then the resolution takes it as the plain revision it stands for
|
|
240
|
+
if ((t.revision === 'moveFrom' || t.revision === 'moveTo') && !this.unreplayed.has(change))
|
|
241
|
+
return;
|
|
242
|
+
const kept = (t.revision === 'ins' || t.revision === 'moveTo') === this.accepted;
|
|
243
|
+
if (!kept)
|
|
244
|
+
this.removeRevision(t.element, t.owner);
|
|
245
|
+
return;
|
|
246
|
+
}
|
|
247
|
+
case 'mark':
|
|
248
|
+
if (change.paragraph && (t.mark === 'ins') !== this.accepted)
|
|
249
|
+
this.marksGone.add(change.paragraph.p);
|
|
250
|
+
return;
|
|
251
|
+
case 'row':
|
|
252
|
+
if ((t.row === 'ins') === this.accepted) {
|
|
253
|
+
for (const inner of t.inner)
|
|
254
|
+
this.plan(inner);
|
|
255
|
+
}
|
|
256
|
+
else
|
|
257
|
+
this.removed.add(t.tr.value);
|
|
258
|
+
return;
|
|
259
|
+
case 'group':
|
|
260
|
+
for (const piece of t.pieces)
|
|
261
|
+
this.plan(piece);
|
|
262
|
+
return;
|
|
263
|
+
case 'field':
|
|
264
|
+
// Word's inserted field: rejected, the whole field goes, its separator and result too
|
|
265
|
+
for (const el of t.span) {
|
|
266
|
+
if (revisionKindOf(el) === 'ins') {
|
|
267
|
+
if (!this.accepted)
|
|
268
|
+
this.removeRevision(el, t.owner);
|
|
269
|
+
}
|
|
270
|
+
else if (!this.accepted && typeNameOf(el) === 'org_docx4j_wml.R')
|
|
271
|
+
this.removed.add(el.value);
|
|
272
|
+
}
|
|
273
|
+
return;
|
|
274
|
+
case 'mathRun':
|
|
275
|
+
if ((t.revision === 'ins') !== this.accepted)
|
|
276
|
+
this.removed.add(t.item.value);
|
|
277
|
+
return;
|
|
278
|
+
case 'mathStructure':
|
|
279
|
+
if ((t.revision === 'ins') !== this.accepted && t.structure)
|
|
280
|
+
this.removed.add(t.structure.value);
|
|
281
|
+
return;
|
|
282
|
+
case 'cell':
|
|
283
|
+
if ((t.cell === 'ins') !== this.accepted)
|
|
284
|
+
this.removed.add(t.tc.value);
|
|
285
|
+
return;
|
|
286
|
+
case 'holder':
|
|
287
|
+
// a content control inserted keeps its content either way; rejected, the control itself goes. One deleted
|
|
288
|
+
// whole (Word's customXmlDelRange form), accepted, goes with everything in it; rejected, it stays (docx4j
|
|
289
|
+
// CR-043 section 17, check 54 cases 15 and 17)
|
|
290
|
+
if (t.revision === 'ins') {
|
|
291
|
+
if (!this.accepted)
|
|
292
|
+
this.unwrapped.add(t.holder.value);
|
|
293
|
+
}
|
|
294
|
+
else if (this.accepted)
|
|
295
|
+
this.removed.add(t.holder.value);
|
|
296
|
+
return;
|
|
297
|
+
default:
|
|
298
|
+
// property records change no text
|
|
299
|
+
}
|
|
300
|
+
}
|
|
301
|
+
/**
|
|
302
|
+
* `removeRevision`: the revision goes, and the comments whose range started on it, or whose markers
|
|
303
|
+
* lie either side of it in its list, are candidates; so is one with a marker in its list on the
|
|
304
|
+
* revision's side and the other in another paragraph (docx4j's U23).
|
|
305
|
+
*/
|
|
306
|
+
removeRevision(item, owner) {
|
|
307
|
+
this.removed.add(item.value);
|
|
308
|
+
const inner = listOf(item.value);
|
|
309
|
+
const at = owner.indexOf(item);
|
|
310
|
+
if (!inner || at < 0)
|
|
311
|
+
return;
|
|
312
|
+
for (const o of inner) {
|
|
313
|
+
if (localName(o) !== 'commentRangeStart')
|
|
314
|
+
continue;
|
|
315
|
+
const id = commentIdOf(o);
|
|
316
|
+
if (markerAt(owner, at + 1, owner.length, 'commentRangeEnd', id) >= 0)
|
|
317
|
+
this.commentCandidates.push(new CommentCandidate(this, id, owner, at));
|
|
318
|
+
else
|
|
319
|
+
this.spanCandidates.push(new SpanCandidate(this, id, item, owner, at, true));
|
|
320
|
+
}
|
|
321
|
+
for (let s = 0; s < at; s++) {
|
|
322
|
+
if (localName(owner[s]) !== 'commentRangeStart')
|
|
323
|
+
continue;
|
|
324
|
+
const id = commentIdOf(owner[s]);
|
|
325
|
+
if (markerAt(owner, s + 1, owner.length, 'commentRangeEnd', id) < 0)
|
|
326
|
+
this.spanCandidates.push(new SpanCandidate(this, id, item, owner, s + 1, true));
|
|
327
|
+
else if (markerAt(owner, at + 1, owner.length, 'commentRangeEnd', id) >= 0)
|
|
328
|
+
this.commentCandidates.push(new CommentCandidate(this, id, owner, s));
|
|
329
|
+
}
|
|
330
|
+
for (let e = at + 1; e < owner.length; e++) {
|
|
331
|
+
if (localName(owner[e]) === 'commentRangeEnd' && markerAt(owner, 0, e, 'commentRangeStart', commentIdOf(owner[e])) < 0) {
|
|
332
|
+
this.spanCandidates.push(new SpanCandidate(this, commentIdOf(owner[e]), item, owner, e, false));
|
|
333
|
+
}
|
|
334
|
+
}
|
|
335
|
+
}
|
|
336
|
+
/** Records a list member gone (a move's half, the text typed into a rejected move's destination). */
|
|
337
|
+
remove(value) {
|
|
338
|
+
this.removed.add(value);
|
|
339
|
+
}
|
|
340
|
+
/** Records a paragraph mark gone. */
|
|
341
|
+
markGone(p) {
|
|
342
|
+
this.marksGone.add(p);
|
|
343
|
+
}
|
|
344
|
+
/** Records a moved paragraph's mark gone. */
|
|
345
|
+
movedMarkGone(p) {
|
|
346
|
+
this.movedMarksGone.add(p);
|
|
347
|
+
}
|
|
348
|
+
/** Whether run-level content has text in this view, once its removals are made. */
|
|
349
|
+
hasText(item) {
|
|
350
|
+
var _a;
|
|
351
|
+
const v = valueOf(item);
|
|
352
|
+
if (v === undefined || v === null || this.removed.has(v))
|
|
353
|
+
return false;
|
|
354
|
+
if (typeNameOf(v) === 'org_docx4j_wml.R')
|
|
355
|
+
return ((_a = v.content) !== null && _a !== void 0 ? _a : []).some((o) => itemTextOf(o) !== undefined);
|
|
356
|
+
const items = listOf(v);
|
|
357
|
+
return items !== undefined && items.some((o) => this.hasText(o));
|
|
358
|
+
}
|
|
359
|
+
/**
|
|
360
|
+
* Whether anything is left in a paragraph once this view's removals are made: the resolution removes
|
|
361
|
+
* an emptied moved paragraph and joins one that is not. A comment's range markers inside a revision
|
|
362
|
+
* taken away stay behind it.
|
|
363
|
+
*/
|
|
364
|
+
remainsIn(p) {
|
|
365
|
+
var _a;
|
|
366
|
+
for (const item of ((_a = p.content) !== null && _a !== void 0 ? _a : [])) {
|
|
367
|
+
const v = item.value;
|
|
368
|
+
if (!this.removed.has(v))
|
|
369
|
+
return true;
|
|
370
|
+
const inner = listOf(v);
|
|
371
|
+
if (inner && revisionKindOf(item) !== undefined && inner.some((o) => localName(o) === 'commentRangeStart' || localName(o) === 'commentRangeEnd'))
|
|
372
|
+
return true;
|
|
373
|
+
}
|
|
374
|
+
return false;
|
|
375
|
+
}
|
|
376
|
+
}
|
|
377
|
+
/** A comment whose range held a revision taken away, and where its range's text begins to be looked for. */
|
|
378
|
+
class CommentCandidate {
|
|
379
|
+
constructor(view, id, owner, at) {
|
|
380
|
+
this.view = view;
|
|
381
|
+
this.id = id;
|
|
382
|
+
this.owner = owner;
|
|
383
|
+
this.at = at;
|
|
384
|
+
}
|
|
385
|
+
/** `rangeIsEmpty`, on what this view leaves: nothing with text before the range's end, in the same list. */
|
|
386
|
+
rangeEmpty() {
|
|
387
|
+
for (let i = this.at + 1; i < this.owner.length; i++) {
|
|
388
|
+
const item = this.owner[i];
|
|
389
|
+
if (localName(item) === 'commentRangeEnd' && commentIdOf(item) === this.id)
|
|
390
|
+
return true;
|
|
391
|
+
if (this.view.hasText(item))
|
|
392
|
+
return false;
|
|
393
|
+
}
|
|
394
|
+
return false; // the end is elsewhere: text may be
|
|
395
|
+
}
|
|
396
|
+
}
|
|
397
|
+
/**
|
|
398
|
+
* A comment whose range held a revision taken away, its start and end in different paragraphs of one
|
|
399
|
+
* list: gone, as `settleSpanningComments` judges it once the joins are made, when every paragraph from
|
|
400
|
+
* the start's up to the end's loses its mark (so that they join), with nothing between them but range
|
|
401
|
+
* markers and what this view removes, and nothing with text in the range.
|
|
402
|
+
*/
|
|
403
|
+
class SpanCandidate {
|
|
404
|
+
constructor(view, id, revision, owner, at, startHere) {
|
|
405
|
+
this.view = view;
|
|
406
|
+
this.id = id;
|
|
407
|
+
this.revision = revision;
|
|
408
|
+
this.owner = owner;
|
|
409
|
+
this.at = at;
|
|
410
|
+
this.startHere = startHere;
|
|
411
|
+
}
|
|
412
|
+
rangeEmpty() {
|
|
413
|
+
const here = this.revision.value.PARENT;
|
|
414
|
+
if (typeNameOf(here) !== 'org_docx4j_wml.P' || here.content !== this.owner)
|
|
415
|
+
return false;
|
|
416
|
+
const container = listOf(here.PARENT);
|
|
417
|
+
if (!container)
|
|
418
|
+
return false;
|
|
419
|
+
let k = container.findIndex((el) => el.value === here);
|
|
420
|
+
if (k < 0)
|
|
421
|
+
return false;
|
|
422
|
+
const view = this.view;
|
|
423
|
+
const contentOf = (p) => { var _a; return ((_a = p.content) !== null && _a !== void 0 ? _a : []); };
|
|
424
|
+
if (this.startHere) {
|
|
425
|
+
for (let i = this.at; i < this.owner.length; i++)
|
|
426
|
+
if (view.hasText(this.owner[i]))
|
|
427
|
+
return false;
|
|
428
|
+
let p = here;
|
|
429
|
+
for (;;) {
|
|
430
|
+
if (!view.removesMark(p))
|
|
431
|
+
return false; // a mark left between start and end (U24)
|
|
432
|
+
k++;
|
|
433
|
+
while (k < container.length && this.skipped(container[k])) {
|
|
434
|
+
if (this.isMarker(container[k], 'commentRangeEnd'))
|
|
435
|
+
return true;
|
|
436
|
+
k++;
|
|
437
|
+
}
|
|
438
|
+
if (k >= container.length || typeNameOf(container[k]) !== 'org_docx4j_wml.P')
|
|
439
|
+
return false;
|
|
440
|
+
p = container[k].value;
|
|
441
|
+
const items = contentOf(p);
|
|
442
|
+
const end = markerAt(items, 0, items.length, 'commentRangeEnd', this.id);
|
|
443
|
+
const to = end < 0 ? items.length : end;
|
|
444
|
+
for (let i = 0; i < to; i++)
|
|
445
|
+
if (view.hasText(items[i]))
|
|
446
|
+
return false;
|
|
447
|
+
if (end >= 0)
|
|
448
|
+
return true;
|
|
449
|
+
}
|
|
450
|
+
}
|
|
451
|
+
for (let i = 0; i < this.at; i++)
|
|
452
|
+
if (view.hasText(this.owner[i]))
|
|
453
|
+
return false;
|
|
454
|
+
for (;;) {
|
|
455
|
+
k--;
|
|
456
|
+
while (k >= 0 && this.skipped(container[k])) {
|
|
457
|
+
if (this.isMarker(container[k], 'commentRangeStart'))
|
|
458
|
+
return true;
|
|
459
|
+
k--;
|
|
460
|
+
}
|
|
461
|
+
if (k < 0 || typeNameOf(container[k]) !== 'org_docx4j_wml.P')
|
|
462
|
+
return false;
|
|
463
|
+
const p = container[k].value;
|
|
464
|
+
if (!view.removesMark(p))
|
|
465
|
+
return false; // a mark left between start and end (U24)
|
|
466
|
+
const items = contentOf(p);
|
|
467
|
+
const start = markerAt(items, 0, items.length, 'commentRangeStart', this.id);
|
|
468
|
+
for (let i = start + 1; i < items.length; i++)
|
|
469
|
+
if (view.hasText(items[i]))
|
|
470
|
+
return false;
|
|
471
|
+
if (start >= 0)
|
|
472
|
+
return true;
|
|
473
|
+
}
|
|
474
|
+
}
|
|
475
|
+
/** A range marker between paragraphs, which a join carries along, or a member this view removes. */
|
|
476
|
+
skipped(item) {
|
|
477
|
+
const name = localName(item);
|
|
478
|
+
return name.endsWith('RangeStart') || name.endsWith('RangeEnd') || name === 'bookmarkStart' || name === 'bookmarkEnd'
|
|
479
|
+
|| name === 'permStart' || name === 'permEnd' || name === 'proofErr'
|
|
480
|
+
|| (typeNameOf(item) !== 'org_docx4j_wml.P' && this.view.removes(item));
|
|
481
|
+
}
|
|
482
|
+
isMarker(item, kind) {
|
|
483
|
+
return localName(item) === kind && commentIdOf(item) === this.id;
|
|
484
|
+
}
|
|
485
|
+
}
|
|
486
|
+
/**
|
|
487
|
+
* The moves of one story resolved as `Body.acceptAll` and `rejectAll` resolve them (`resolveMove`,
|
|
488
|
+
* `resolveRangelessHalf`, `dissolveBrokenMoves`): last half first; a half in a named range resolves its
|
|
489
|
+
* whole move, a half in none is an insertion or a deletion, and after a broken move what is left unpaired
|
|
490
|
+
* becomes the plain `w:ins` or `w:del` it stands for, resolved as such. docx4j `ResolvedView.MoveReplay`.
|
|
491
|
+
*/
|
|
492
|
+
class MoveReplay {
|
|
493
|
+
constructor(view, story, halves) {
|
|
494
|
+
this.view = view;
|
|
495
|
+
this.halves = halves;
|
|
496
|
+
/** Pieces resolved, or turned plain: no longer move markup. */
|
|
497
|
+
this.done = new Set();
|
|
498
|
+
/** Halves and marks turned into plain revisions. */
|
|
499
|
+
this.plain = [];
|
|
500
|
+
this.pieces = movePiecesOf(story);
|
|
501
|
+
}
|
|
502
|
+
/** Replays the moves; returns the halves the story has no piece for. */
|
|
503
|
+
run() {
|
|
504
|
+
const missing = [];
|
|
505
|
+
for (let i = this.halves.length - 1; i >= 0; i--) {
|
|
506
|
+
const change = this.halves[i];
|
|
507
|
+
const t = change.target;
|
|
508
|
+
if (t.kind !== 'run')
|
|
509
|
+
continue;
|
|
510
|
+
const half = this.pieces.find((piece) => piece.kind === 'half' && piece.element === t.element);
|
|
511
|
+
if (!half || half.kind !== 'half') {
|
|
512
|
+
missing.push(change);
|
|
513
|
+
continue;
|
|
514
|
+
}
|
|
515
|
+
if (this.done.has(half))
|
|
516
|
+
continue;
|
|
517
|
+
if (half.names.length > 0)
|
|
518
|
+
this.named(half);
|
|
519
|
+
else
|
|
520
|
+
this.rangeless(half, change);
|
|
521
|
+
}
|
|
522
|
+
// what became plain is resolved as plain markup, in the next round
|
|
523
|
+
for (const piece of this.plain) {
|
|
524
|
+
const ins = piece.side === 'to';
|
|
525
|
+
if (ins === this.view.accepted)
|
|
526
|
+
continue;
|
|
527
|
+
if (piece.kind === 'half')
|
|
528
|
+
this.view.removeRevision(piece.element, piece.owner);
|
|
529
|
+
else if (piece.kind === 'mark')
|
|
530
|
+
this.view.markGone(piece.paragraph.value);
|
|
531
|
+
}
|
|
532
|
+
return missing;
|
|
533
|
+
}
|
|
534
|
+
live(piece) {
|
|
535
|
+
return !this.done.has(piece);
|
|
536
|
+
}
|
|
537
|
+
/** `resolveMove`. */
|
|
538
|
+
named(half) {
|
|
539
|
+
const name = half.names[0];
|
|
540
|
+
const ids = new Set();
|
|
541
|
+
for (const piece of this.pieces)
|
|
542
|
+
if (this.live(piece) && piece.kind === 'start' && piece.name === name)
|
|
543
|
+
ids.add(piece.id);
|
|
544
|
+
const mine = this.pieces.filter((piece) => this.live(piece) && ((piece.kind === 'start' && piece.name === name) || (piece.kind === 'end' && ids.has(piece.id))
|
|
545
|
+
|| ((piece.kind === 'half' || piece.kind === 'mark' || piece.kind === 'inner') && piece.names.includes(name))));
|
|
546
|
+
const orphan = !mine.some((piece) => piece.side === 'from');
|
|
547
|
+
const keptFrom = !(this.view.accepted || orphan);
|
|
548
|
+
const broken = orphan || !mine.some((piece) => piece.side === 'to');
|
|
549
|
+
for (const piece of mine) {
|
|
550
|
+
this.done.add(piece);
|
|
551
|
+
if (piece.kind === 'inner' && piece.side === 'to' && keptFrom)
|
|
552
|
+
this.view.remove(piece.element.value);
|
|
553
|
+
if (piece.kind === 'half' && (piece.side === 'from') !== keptFrom)
|
|
554
|
+
this.view.remove(piece.element.value);
|
|
555
|
+
if (piece.kind === 'mark' && (piece.side === 'from') !== keptFrom)
|
|
556
|
+
this.view.movedMarkGone(piece.paragraph.value);
|
|
557
|
+
}
|
|
558
|
+
if (broken)
|
|
559
|
+
this.dissolveBroken();
|
|
560
|
+
}
|
|
561
|
+
/** `resolveRangelessHalf`. */
|
|
562
|
+
rangeless(half, change) {
|
|
563
|
+
const keep = (half.side === 'to') === this.view.accepted;
|
|
564
|
+
this.done.add(half);
|
|
565
|
+
if (!keep)
|
|
566
|
+
this.view.remove(half.element.value);
|
|
567
|
+
const paragraph = change.paragraph;
|
|
568
|
+
if (paragraph) {
|
|
569
|
+
for (const piece of this.pieces) {
|
|
570
|
+
if (!this.live(piece) || piece.kind !== 'mark' || piece.side !== half.side || piece.paragraph !== paragraph.element || piece.names.length > 0)
|
|
571
|
+
continue;
|
|
572
|
+
this.done.add(piece);
|
|
573
|
+
if (!keep)
|
|
574
|
+
this.view.movedMarkGone(piece.paragraph.value);
|
|
575
|
+
break;
|
|
576
|
+
}
|
|
577
|
+
}
|
|
578
|
+
this.dissolveBroken();
|
|
579
|
+
}
|
|
580
|
+
/** `dissolveBrokenMoves`: every half and mark that cannot be paired becomes plain. */
|
|
581
|
+
dissolveBroken() {
|
|
582
|
+
const named = { from: new Set(), to: new Set() };
|
|
583
|
+
for (const piece of this.pieces)
|
|
584
|
+
if (this.live(piece) && piece.kind === 'start')
|
|
585
|
+
named[piece.side].add(piece.name);
|
|
586
|
+
for (const piece of this.pieces) {
|
|
587
|
+
if (!this.live(piece) || (piece.kind !== 'half' && piece.kind !== 'mark'))
|
|
588
|
+
continue;
|
|
589
|
+
const other = named[piece.side === 'from' ? 'to' : 'from'];
|
|
590
|
+
if (piece.names.some((n) => other.has(n)))
|
|
591
|
+
continue;
|
|
592
|
+
this.done.add(piece);
|
|
593
|
+
this.plain.push(piece);
|
|
594
|
+
}
|
|
595
|
+
}
|
|
596
|
+
}
|
|
@@ -7,7 +7,9 @@ import { type ChangeTracker } from './tracking.mjs';
|
|
|
7
7
|
import { type TableLayoutMode } from './tableColumns.mjs';
|
|
8
8
|
/**
|
|
9
9
|
* A subset of Office JS `Word.Table` over a `w:tbl`. Rows are read through row-level content
|
|
10
|
-
* controls (an OpenDoPE repeat wraps its `w:tr` in a `w:sdt`),
|
|
10
|
+
* controls (an OpenDoPE repeat wraps its `w:tr` in a `w:sdt`), and through the selected branch of a
|
|
11
|
+
* kept row-level `mc:AlternateContent` (CR-013 phase 2), so `rows` is what Word shows. A table, row or
|
|
12
|
+
* cell in a branch is read-only (D4), and so is a write that would reach one.
|
|
11
13
|
*/
|
|
12
14
|
export declare class Table {
|
|
13
15
|
/** The `w:tbl` element pair. */
|
|
@@ -28,6 +30,13 @@ export declare class Table {
|
|
|
28
30
|
get index(): number;
|
|
29
31
|
get rowCount(): number;
|
|
30
32
|
get rows(): TableRow[];
|
|
33
|
+
/**
|
|
34
|
+
* The table's range (Office JS `Table.getRange`; CR-014 phase 1): 'Whole' from its first cell's start to its
|
|
35
|
+
* last cell's end, its text the table's in `body.text`'s form, every row ended `\r\n` as Word 365 gives it
|
|
36
|
+
* (check 52); 'Start' and 'End' collapsed at those two ends, and 'After' at the start of the paragraph after
|
|
37
|
+
* the table.
|
|
38
|
+
*/
|
|
39
|
+
getRange(location?: 'Whole' | 'Start' | 'End' | 'After'): Range;
|
|
31
40
|
/** The text of every cell, row by row (Office JS values). */
|
|
32
41
|
get values(): string[][];
|
|
33
42
|
set values(values: string[][]);
|
|
@@ -82,11 +91,15 @@ export declare class Table {
|
|
|
82
91
|
get changeTracker(): ChangeTracker | undefined;
|
|
83
92
|
/** The cell this table is nested in, if any (extension). */
|
|
84
93
|
get parentTableCell(): TableCell | undefined;
|
|
85
|
-
/** The text of the table: a line per paragraph,
|
|
94
|
+
/** The text of the table: a line per paragraph, each `Paragraph.text` (extension; CR-012 phase 4). */
|
|
86
95
|
get text(): string;
|
|
87
96
|
/** The column widths in twips, from the grid or from the first row (extension). */
|
|
88
97
|
columnWidths(): number[];
|
|
89
98
|
private tblPr;
|
|
99
|
+
/** True for a table in the selected branch of a kept block-level `mc:AlternateContent` (CR-013 phase 2): read-only (D4). */
|
|
100
|
+
get inBranch(): boolean;
|
|
101
|
+
/** Refuses a write to a table in a branch (CR-013 D4). Internal: the table's mutators call it first. */
|
|
102
|
+
assertWritable(): void;
|
|
90
103
|
}
|
|
91
104
|
/** A subset of Office JS `Word.TableRow` over a `w:tr`. */
|
|
92
105
|
export declare class TableRow {
|
|
@@ -112,6 +125,12 @@ export declare class TableRow {
|
|
|
112
125
|
insertRows(location: 'Before' | 'After', rowCount: number, values?: string[][]): TableRow[];
|
|
113
126
|
/** Removes the row; tracked, it stays and takes a `w:trPr/w:del` (CR-002 phase F). */
|
|
114
127
|
delete(): void;
|
|
128
|
+
/** True for a row in a branch of a kept `mc:AlternateContent`, or in a table in one (CR-013 phase 2): read-only (D4). */
|
|
129
|
+
get inBranch(): boolean;
|
|
130
|
+
/** Refuses a write to a row in a branch (CR-013 D4). Internal. */
|
|
131
|
+
assertWritable(): void;
|
|
132
|
+
/** Refuses `values` of `count` cells where the row, or one of those cells, is in a branch. Internal. */
|
|
133
|
+
assertValuesWritable(count: number): void;
|
|
115
134
|
private trPrItem;
|
|
116
135
|
}
|
|
117
136
|
/** A subset of Office JS `Word.TableCell` over a `w:tc`: a body of its own, plus its position. */
|
|
@@ -134,7 +153,10 @@ export declare class TableCell {
|
|
|
134
153
|
get body(): Body;
|
|
135
154
|
get paragraphs(): Paragraph[];
|
|
136
155
|
get tables(): Table[];
|
|
137
|
-
/**
|
|
156
|
+
/**
|
|
157
|
+
* The cell's text as Office JS's `tableCell.value` gives it: its body's text (`Body.text`), its paragraphs'
|
|
158
|
+
* `Paragraph.text` a mark `\r` apart (check 51: `value`, `values` and `body.text` alike).
|
|
159
|
+
*/
|
|
138
160
|
get text(): string;
|
|
139
161
|
/** Office JS TableCell.value: the text, replaced as one paragraph when set. */
|
|
140
162
|
get value(): string;
|
|
@@ -157,6 +179,10 @@ export declare class TableCell {
|
|
|
157
179
|
insertColumns(location: 'Before' | 'After', columnCount: number, values?: string[][]): TableCell[][];
|
|
158
180
|
/** Removes the grid columns this cell covers (Office JS `TableCell.deleteColumn`); tracked as `Table.deleteColumns` is. */
|
|
159
181
|
deleteColumn(): void;
|
|
182
|
+
/** True for a cell in a branch of a kept `mc:AlternateContent`, or in a row or table in one (CR-013 phase 2): read-only (D4). */
|
|
183
|
+
get inBranch(): boolean;
|
|
184
|
+
/** Refuses a write to a cell in a branch (CR-013 D4); its body's writes refuse too. Internal. */
|
|
185
|
+
assertWritable(): void;
|
|
160
186
|
/** Office JS TableCell.columnWidth, the same value. */
|
|
161
187
|
get columnWidth(): number;
|
|
162
188
|
set columnWidth(points: number);
|