@a3s-lab/office 0.1.0 → 0.2.2
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/README.md +101 -24
- package/dist/0~2582.js +485 -0
- package/dist/0~4595.js +14 -7
- package/dist/0~4750.js +939 -0
- package/dist/{0~work-document-paragraph-formatting.js → 0~5861.js} +174 -3
- package/dist/0~7048.js +8 -6
- package/dist/0~9512.js +7 -4
- package/dist/0~document-editor.js +3147 -531
- package/dist/0~markdown-editor.js +26 -1
- package/dist/0~presentation-editor.js +68 -12
- package/dist/0~spreadsheet-editor.js +37 -17
- package/dist/0~work-document-extensions.js +588 -13
- package/dist/0~work-document-model-codec.js +1 -1
- package/dist/0~work-docx-bibliography.js +1 -1
- package/dist/0~work-docx-export.js +116 -55
- package/dist/0~work-docx-import.js +766 -107
- package/dist/0~work-office-diagnostics.js +2 -2
- package/dist/{4704.js → 2881.js} +162 -71
- package/dist/4104.js +2 -62
- package/dist/internal/features/work/editors/document-comment-window.d.ts +37 -0
- package/dist/internal/features/work/editors/document-navigation-panel.d.ts +3 -1
- package/dist/internal/features/work/editors/document-navigation-window.d.ts +64 -0
- package/dist/internal/features/work/editors/document-outline-navigation.d.ts +11 -0
- package/dist/internal/features/work/editors/document-page-navigation.d.ts +11 -1
- package/dist/internal/features/work/editors/document-page-thumbnail.d.ts +31 -0
- package/dist/internal/features/work/editors/document-picture-properties-dialog-model.d.ts +28 -0
- package/dist/internal/features/work/editors/document-picture-properties-dialog.d.ts +4 -0
- package/dist/internal/features/work/editors/document-search-navigation.d.ts +12 -0
- package/dist/internal/features/work/editors/document-table-margins-popover.d.ts +4 -0
- package/dist/internal/features/work/editors/document-table-properties-dialog-model.d.ts +51 -0
- package/dist/internal/features/work/editors/document-table-properties-dialog-sections.d.ts +19 -0
- package/dist/internal/features/work/editors/document-table-properties-dialog.d.ts +8 -0
- package/dist/internal/features/work/editors/office-task-pane.d.ts +1 -1
- package/dist/internal/features/work/editors/presentation-chart-panel.d.ts +2 -1
- package/dist/internal/features/work/editors/presentation-comments-panel.d.ts +2 -1
- package/dist/internal/features/work/editors/spreadsheet-workbook-panel.d.ts +2 -1
- package/dist/internal/features/work/editors/use-document-pagination.d.ts +6 -0
- package/dist/internal/features/work/editors/use-presentation-review-commands.d.ts +1 -1
- package/dist/internal/features/work/work-document-image-layout.d.ts +11 -0
- package/dist/internal/features/work/work-document-page-capture.d.ts +15 -0
- package/dist/internal/features/work/work-document-paragraph-formatting.d.ts +4 -0
- package/dist/internal/features/work/work-document-section.d.ts +3 -1
- package/dist/internal/features/work/work-document-table-borders.d.ts +20 -0
- package/dist/internal/features/work/work-document-table-cell-formatting.d.ts +8 -5
- package/dist/internal/features/work/work-document-table-geometry.d.ts +41 -0
- package/dist/internal/features/work/work-document-table-property-changes.d.ts +25 -0
- package/dist/internal/features/work/work-document-table-sizing.d.ts +15 -2
- package/dist/internal/features/work/work-document-word-line-metrics.d.ts +11 -0
- package/dist/internal/features/work/work-docx-document-layout.d.ts +2 -0
- package/dist/internal/features/work/work-docx-paragraph-alignment-import.d.ts +2 -1
- package/dist/internal/features/work/work-docx-paragraph-direction-import.d.ts +2 -1
- package/dist/internal/features/work/work-docx-paragraph-indent-import.d.ts +2 -1
- package/dist/internal/features/work/work-docx-paragraph-pagination-import.d.ts +2 -1
- package/dist/internal/features/work/work-docx-paragraph-spacing-import.d.ts +3 -2
- package/dist/internal/features/work/work-docx-paragraph-styles.d.ts +2 -2
- package/dist/internal/features/work/work-docx-run-formatting-import.d.ts +8 -1
- package/dist/internal/features/work/work-docx-tab-stop-import.d.ts +2 -1
- package/dist/internal/features/work/work-docx-table-cell-export.d.ts +1 -1
- package/dist/internal/features/work/work-docx-table-cell-import.d.ts +14 -4
- package/dist/internal/features/work/work-docx-table-sizing-export.d.ts +1 -1
- package/dist/internal/features/work/work-docx-table-sizing-import.d.ts +4 -3
- package/dist/internal/features/work/work-docx-table-styles.d.ts +22 -0
- package/dist/internal/features/work/work-types.d.ts +6 -0
- package/dist/office-kernel.wasm +0 -0
- package/dist/styles.css +1288 -233
- package/docs/{browser-editor-architecture.md → latest/en/browser-editor-architecture.md} +144 -35
- package/package.json +9 -5
- package/dist/0~6552.js +0 -787
- package/dist/0~8155.js +0 -299
package/dist/0~6552.js
DELETED
|
@@ -1,787 +0,0 @@
|
|
|
1
|
-
import { Extension } from "@tiptap/core";
|
|
2
|
-
import { Table, TableCell, TableHeader, TableRow, TableView } from "@tiptap/extension-table";
|
|
3
|
-
import { NodeSelection, Plugin } from "@tiptap/pm/state";
|
|
4
|
-
import { CellSelection, TableMap, isInTable, selectedRect } from "@tiptap/pm/tables";
|
|
5
|
-
const DOCUMENT_TABLE_STYLE_OPTIONS = [
|
|
6
|
-
{
|
|
7
|
-
id: 'grid',
|
|
8
|
-
label: '网格',
|
|
9
|
-
headerColor: '#f1f4f9',
|
|
10
|
-
bodyColor: '#ffffff',
|
|
11
|
-
alternateColor: '#ffffff',
|
|
12
|
-
borderColor: '#cfd5df',
|
|
13
|
-
borderStyle: 'solid',
|
|
14
|
-
borderWidth: 1
|
|
15
|
-
},
|
|
16
|
-
{
|
|
17
|
-
id: 'blueStripe',
|
|
18
|
-
label: '蓝色条纹',
|
|
19
|
-
headerColor: '#d9eaf7',
|
|
20
|
-
bodyColor: '#ffffff',
|
|
21
|
-
alternateColor: '#f7fbff',
|
|
22
|
-
borderColor: '#9fbad0',
|
|
23
|
-
borderStyle: 'solid',
|
|
24
|
-
borderWidth: 1
|
|
25
|
-
},
|
|
26
|
-
{
|
|
27
|
-
id: 'greenStripe',
|
|
28
|
-
label: '绿色条纹',
|
|
29
|
-
headerColor: '#ddeee7',
|
|
30
|
-
bodyColor: '#ffffff',
|
|
31
|
-
alternateColor: '#f4faf7',
|
|
32
|
-
borderColor: '#abc8be',
|
|
33
|
-
borderStyle: 'solid',
|
|
34
|
-
borderWidth: 1
|
|
35
|
-
},
|
|
36
|
-
{
|
|
37
|
-
id: 'grayStripe',
|
|
38
|
-
label: '灰色条纹',
|
|
39
|
-
headerColor: '#e7e9ed',
|
|
40
|
-
bodyColor: '#ffffff',
|
|
41
|
-
alternateColor: '#f6f7f9',
|
|
42
|
-
borderColor: '#b9c0ca',
|
|
43
|
-
borderStyle: 'solid',
|
|
44
|
-
borderWidth: 1
|
|
45
|
-
},
|
|
46
|
-
{
|
|
47
|
-
id: 'clean',
|
|
48
|
-
label: '简洁',
|
|
49
|
-
headerColor: '#f1f4f9',
|
|
50
|
-
bodyColor: '#ffffff',
|
|
51
|
-
alternateColor: '#ffffff',
|
|
52
|
-
borderColor: '#cfd5df',
|
|
53
|
-
borderStyle: 'none',
|
|
54
|
-
borderWidth: 0
|
|
55
|
-
}
|
|
56
|
-
];
|
|
57
|
-
const DEFAULT_DOCUMENT_TABLE_CELL_FORMAT = {
|
|
58
|
-
backgroundColor: '#ffffff',
|
|
59
|
-
verticalAlign: 'top',
|
|
60
|
-
borderColor: '#cfd5df',
|
|
61
|
-
borderStyle: 'solid',
|
|
62
|
-
borderWidth: 1
|
|
63
|
-
};
|
|
64
|
-
const DEFAULT_DOCUMENT_TABLE_HEADER_FORMAT = {
|
|
65
|
-
...DEFAULT_DOCUMENT_TABLE_CELL_FORMAT,
|
|
66
|
-
backgroundColor: '#f1f4f9'
|
|
67
|
-
};
|
|
68
|
-
const DocumentTableCell = TableCell.extend({
|
|
69
|
-
addAttributes () {
|
|
70
|
-
return {
|
|
71
|
-
...this.parent?.(),
|
|
72
|
-
...documentTableCellAttributes(DEFAULT_DOCUMENT_TABLE_CELL_FORMAT)
|
|
73
|
-
};
|
|
74
|
-
}
|
|
75
|
-
});
|
|
76
|
-
const DocumentTableHeader = TableHeader.extend({
|
|
77
|
-
addAttributes () {
|
|
78
|
-
return {
|
|
79
|
-
...this.parent?.(),
|
|
80
|
-
...documentTableCellAttributes(DEFAULT_DOCUMENT_TABLE_HEADER_FORMAT)
|
|
81
|
-
};
|
|
82
|
-
}
|
|
83
|
-
});
|
|
84
|
-
const DocumentTableFormatting = Extension.create({
|
|
85
|
-
name: 'documentTableFormatting',
|
|
86
|
-
addCommands () {
|
|
87
|
-
return {
|
|
88
|
-
setDocumentTableCellFormat: (format)=>(props)=>setSelectedCellFormat(props, format),
|
|
89
|
-
setDocumentTableHorizontalAlignment: (alignment)=>(props)=>setSelectedCellAlignment(props, alignment),
|
|
90
|
-
applyDocumentTableStyle: (style)=>(props)=>applyTableStyle(props, style)
|
|
91
|
-
};
|
|
92
|
-
}
|
|
93
|
-
});
|
|
94
|
-
function documentTableCellFormat(state) {
|
|
95
|
-
const position = selectedTableCellPositions(state.selection)[0];
|
|
96
|
-
const node = void 0 === position ? null : state.doc.nodeAt(position);
|
|
97
|
-
return node && isTableCell(node) ? formatFromAttributes(node.attrs) : null;
|
|
98
|
-
}
|
|
99
|
-
function documentTableHorizontalAlignment(state) {
|
|
100
|
-
const position = selectedTableCellPositions(state.selection)[0];
|
|
101
|
-
const cell = void 0 === position ? null : state.doc.nodeAt(position);
|
|
102
|
-
let alignment = 'left';
|
|
103
|
-
cell?.descendants((node)=>{
|
|
104
|
-
if ('paragraph' !== node.type.name && 'heading' !== node.type.name) return true;
|
|
105
|
-
if ('center' === node.attrs.textAlign || 'right' === node.attrs.textAlign) alignment = node.attrs.textAlign;
|
|
106
|
-
return false;
|
|
107
|
-
});
|
|
108
|
-
return alignment;
|
|
109
|
-
}
|
|
110
|
-
function activeDocumentTableStyle(state) {
|
|
111
|
-
const context = selectedTable(state.selection);
|
|
112
|
-
if (!context) return null;
|
|
113
|
-
for (const style of DOCUMENT_TABLE_STYLE_OPTIONS){
|
|
114
|
-
let matches = true;
|
|
115
|
-
context.node.forEach((row, _rowOffset, rowIndex)=>{
|
|
116
|
-
row.forEach((cell)=>{
|
|
117
|
-
const expected = tableStyleCellFormat(style, cell, rowIndex);
|
|
118
|
-
const actual = formatFromAttributes(cell.attrs);
|
|
119
|
-
if (expected.backgroundColor !== actual.backgroundColor || expected.borderColor !== actual.borderColor || expected.borderStyle !== actual.borderStyle || expected.borderWidth !== actual.borderWidth) matches = false;
|
|
120
|
-
});
|
|
121
|
-
});
|
|
122
|
-
if (matches) return style.id;
|
|
123
|
-
}
|
|
124
|
-
return null;
|
|
125
|
-
}
|
|
126
|
-
function documentTableCellAttributes(defaults) {
|
|
127
|
-
return {
|
|
128
|
-
backgroundColor: {
|
|
129
|
-
default: defaults.backgroundColor,
|
|
130
|
-
parseHTML: (element)=>normalizeTableColor(element.dataset.officeCellFill || element.style.backgroundColor) ?? defaults.backgroundColor,
|
|
131
|
-
renderHTML: (attributes)=>{
|
|
132
|
-
const color = normalizeTableColor(String(attributes.backgroundColor ?? '')) ?? defaults.backgroundColor;
|
|
133
|
-
return {
|
|
134
|
-
'data-office-cell-fill': color,
|
|
135
|
-
style: `background-color: ${color}`
|
|
136
|
-
};
|
|
137
|
-
}
|
|
138
|
-
},
|
|
139
|
-
verticalAlign: {
|
|
140
|
-
default: defaults.verticalAlign,
|
|
141
|
-
parseHTML: (element)=>normalizeDocumentTableVerticalAlign(element.dataset.officeCellVerticalAlign || element.style.verticalAlign) ?? defaults.verticalAlign,
|
|
142
|
-
renderHTML: (attributes)=>{
|
|
143
|
-
const alignment = normalizeDocumentTableVerticalAlign(String(attributes.verticalAlign ?? '')) ?? defaults.verticalAlign;
|
|
144
|
-
return {
|
|
145
|
-
'data-office-cell-vertical-align': alignment,
|
|
146
|
-
style: `vertical-align: ${alignment}`
|
|
147
|
-
};
|
|
148
|
-
}
|
|
149
|
-
},
|
|
150
|
-
borderColor: {
|
|
151
|
-
default: defaults.borderColor,
|
|
152
|
-
parseHTML: (element)=>normalizeTableColor(element.dataset.officeCellBorderColor || element.style.borderColor) ?? defaults.borderColor,
|
|
153
|
-
renderHTML: (attributes)=>{
|
|
154
|
-
const format = formatFromAttributes(attributes, defaults);
|
|
155
|
-
return {
|
|
156
|
-
'data-office-cell-border-color': format.borderColor,
|
|
157
|
-
'data-office-cell-border-style': format.borderStyle,
|
|
158
|
-
'data-office-cell-border-width': String(format.borderWidth),
|
|
159
|
-
style: 'none' === format.borderStyle || 0 === format.borderWidth ? 'border: 0 none transparent' : `border: ${format.borderWidth}px ${format.borderStyle} ${format.borderColor}`
|
|
160
|
-
};
|
|
161
|
-
}
|
|
162
|
-
},
|
|
163
|
-
borderStyle: {
|
|
164
|
-
default: defaults.borderStyle,
|
|
165
|
-
parseHTML: (element)=>normalizeDocumentTableBorderStyle(element.dataset.officeCellBorderStyle || element.style.borderStyle) ?? defaults.borderStyle,
|
|
166
|
-
renderHTML: ()=>({})
|
|
167
|
-
},
|
|
168
|
-
borderWidth: {
|
|
169
|
-
default: defaults.borderWidth,
|
|
170
|
-
parseHTML: (element)=>normalizeDocumentTableBorderWidth(element.dataset.officeCellBorderWidth || element.style.borderWidth) ?? defaults.borderWidth,
|
|
171
|
-
renderHTML: ()=>({})
|
|
172
|
-
}
|
|
173
|
-
};
|
|
174
|
-
}
|
|
175
|
-
function setSelectedCellFormat({ dispatch, state }, patch) {
|
|
176
|
-
const normalized = normalizeFormatPatch(patch);
|
|
177
|
-
if (!normalized) return false;
|
|
178
|
-
const positions = selectedTableCellPositions(state.selection);
|
|
179
|
-
if (!positions.length) return false;
|
|
180
|
-
const transaction = state.tr;
|
|
181
|
-
for (const position of positions){
|
|
182
|
-
const cell = transaction.doc.nodeAt(position);
|
|
183
|
-
if (cell && isTableCell(cell)) transaction.setNodeMarkup(position, void 0, {
|
|
184
|
-
...cell.attrs,
|
|
185
|
-
...normalized
|
|
186
|
-
});
|
|
187
|
-
}
|
|
188
|
-
if (dispatch && transaction.docChanged) dispatch(transaction.scrollIntoView());
|
|
189
|
-
return true;
|
|
190
|
-
}
|
|
191
|
-
function setSelectedCellAlignment({ dispatch, state }, alignment) {
|
|
192
|
-
if ('left' !== alignment && 'center' !== alignment && 'right' !== alignment) return false;
|
|
193
|
-
const positions = selectedTableCellPositions(state.selection);
|
|
194
|
-
if (!positions.length) return false;
|
|
195
|
-
const transaction = state.tr;
|
|
196
|
-
for (const position of positions){
|
|
197
|
-
const cell = transaction.doc.nodeAt(position);
|
|
198
|
-
if (cell && isTableCell(cell)) cell.descendants((node, offset)=>{
|
|
199
|
-
if ('paragraph' !== node.type.name && 'heading' !== node.type.name) return true;
|
|
200
|
-
transaction.setNodeMarkup(position + 1 + offset, void 0, {
|
|
201
|
-
...node.attrs,
|
|
202
|
-
textAlign: alignment
|
|
203
|
-
});
|
|
204
|
-
return false;
|
|
205
|
-
});
|
|
206
|
-
}
|
|
207
|
-
if (dispatch && transaction.docChanged) dispatch(transaction.scrollIntoView());
|
|
208
|
-
return true;
|
|
209
|
-
}
|
|
210
|
-
function applyTableStyle({ dispatch, state }, styleId) {
|
|
211
|
-
const style = DOCUMENT_TABLE_STYLE_OPTIONS.find((candidate)=>candidate.id === styleId);
|
|
212
|
-
const context = selectedTable(state.selection);
|
|
213
|
-
if (!style || !context) return false;
|
|
214
|
-
const transaction = state.tr;
|
|
215
|
-
context.node.forEach((row, rowOffset, rowIndex)=>{
|
|
216
|
-
row.forEach((cell, cellOffset)=>{
|
|
217
|
-
const position = context.position + 2 + rowOffset + cellOffset;
|
|
218
|
-
transaction.setNodeMarkup(position, void 0, {
|
|
219
|
-
...cell.attrs,
|
|
220
|
-
...tableStyleCellFormat(style, cell, rowIndex)
|
|
221
|
-
});
|
|
222
|
-
});
|
|
223
|
-
});
|
|
224
|
-
if (dispatch && transaction.docChanged) dispatch(transaction.scrollIntoView());
|
|
225
|
-
return true;
|
|
226
|
-
}
|
|
227
|
-
function selectedTableCellPositions(selection) {
|
|
228
|
-
if (selection instanceof CellSelection) {
|
|
229
|
-
const positions = [];
|
|
230
|
-
selection.forEachCell((_node, position)=>positions.push(position));
|
|
231
|
-
return positions;
|
|
232
|
-
}
|
|
233
|
-
if (selection instanceof NodeSelection && 'table' === selection.node.type.spec.tableRole) {
|
|
234
|
-
const positions = [];
|
|
235
|
-
selection.node.forEach((row, rowOffset)=>{
|
|
236
|
-
row.forEach((_cell, cellOffset)=>{
|
|
237
|
-
positions.push(selection.from + 2 + rowOffset + cellOffset);
|
|
238
|
-
});
|
|
239
|
-
});
|
|
240
|
-
return positions;
|
|
241
|
-
}
|
|
242
|
-
const position = ancestorPosition(selection.$from, isTableCell);
|
|
243
|
-
return null === position ? [] : [
|
|
244
|
-
position
|
|
245
|
-
];
|
|
246
|
-
}
|
|
247
|
-
function selectedTable(selection) {
|
|
248
|
-
if (selection instanceof NodeSelection && 'table' === selection.node.type.spec.tableRole) return {
|
|
249
|
-
node: selection.node,
|
|
250
|
-
position: selection.from
|
|
251
|
-
};
|
|
252
|
-
for(let depth = selection.$from.depth; depth > 0; depth -= 1){
|
|
253
|
-
const node = selection.$from.node(depth);
|
|
254
|
-
if ('table' === node.type.spec.tableRole) return {
|
|
255
|
-
node,
|
|
256
|
-
position: selection.$from.before(depth)
|
|
257
|
-
};
|
|
258
|
-
}
|
|
259
|
-
return null;
|
|
260
|
-
}
|
|
261
|
-
function ancestorPosition(position, predicate) {
|
|
262
|
-
for(let depth = position.depth; depth > 0; depth -= 1)if (predicate(position.node(depth))) return position.before(depth);
|
|
263
|
-
return null;
|
|
264
|
-
}
|
|
265
|
-
function isTableCell(node) {
|
|
266
|
-
return 'cell' === node.type.spec.tableRole || 'header_cell' === node.type.spec.tableRole;
|
|
267
|
-
}
|
|
268
|
-
function tableStyleCellFormat(style, cell, rowIndex) {
|
|
269
|
-
return {
|
|
270
|
-
backgroundColor: 'header_cell' === cell.type.spec.tableRole ? style.headerColor : rowIndex % 2 === 1 ? style.alternateColor : style.bodyColor,
|
|
271
|
-
borderColor: style.borderColor,
|
|
272
|
-
borderStyle: style.borderStyle,
|
|
273
|
-
borderWidth: style.borderWidth
|
|
274
|
-
};
|
|
275
|
-
}
|
|
276
|
-
function normalizeFormatPatch(patch) {
|
|
277
|
-
const normalized = {};
|
|
278
|
-
if (void 0 !== patch.backgroundColor) {
|
|
279
|
-
const color = normalizeTableColor(patch.backgroundColor);
|
|
280
|
-
if (!color) return null;
|
|
281
|
-
normalized.backgroundColor = color;
|
|
282
|
-
}
|
|
283
|
-
if (void 0 !== patch.verticalAlign) {
|
|
284
|
-
const alignment = normalizeDocumentTableVerticalAlign(patch.verticalAlign);
|
|
285
|
-
if (!alignment) return null;
|
|
286
|
-
normalized.verticalAlign = alignment;
|
|
287
|
-
}
|
|
288
|
-
if (void 0 !== patch.borderColor) {
|
|
289
|
-
const color = normalizeTableColor(patch.borderColor);
|
|
290
|
-
if (!color) return null;
|
|
291
|
-
normalized.borderColor = color;
|
|
292
|
-
}
|
|
293
|
-
if (void 0 !== patch.borderStyle) {
|
|
294
|
-
const style = normalizeDocumentTableBorderStyle(patch.borderStyle);
|
|
295
|
-
if (!style) return null;
|
|
296
|
-
normalized.borderStyle = style;
|
|
297
|
-
}
|
|
298
|
-
if (void 0 !== patch.borderWidth) {
|
|
299
|
-
const width = normalizeDocumentTableBorderWidth(patch.borderWidth);
|
|
300
|
-
if (null === width) return null;
|
|
301
|
-
normalized.borderWidth = width;
|
|
302
|
-
}
|
|
303
|
-
return normalized;
|
|
304
|
-
}
|
|
305
|
-
function formatFromAttributes(attributes, defaults = DEFAULT_DOCUMENT_TABLE_CELL_FORMAT) {
|
|
306
|
-
return {
|
|
307
|
-
backgroundColor: normalizeTableColor(String(attributes.backgroundColor ?? '')) ?? defaults.backgroundColor,
|
|
308
|
-
verticalAlign: normalizeDocumentTableVerticalAlign(String(attributes.verticalAlign ?? '')) ?? defaults.verticalAlign,
|
|
309
|
-
borderColor: normalizeTableColor(String(attributes.borderColor ?? '')) ?? defaults.borderColor,
|
|
310
|
-
borderStyle: normalizeDocumentTableBorderStyle(String(attributes.borderStyle ?? '')) ?? defaults.borderStyle,
|
|
311
|
-
borderWidth: normalizeDocumentTableBorderWidth(attributes.borderWidth) ?? defaults.borderWidth
|
|
312
|
-
};
|
|
313
|
-
}
|
|
314
|
-
function normalizeTableColor(value) {
|
|
315
|
-
const trimmed = value?.trim().toLowerCase();
|
|
316
|
-
if (!trimmed) return null;
|
|
317
|
-
if (/^#[0-9a-f]{3}$/.test(trimmed)) return `#${trimmed.slice(1).split('').map((part)=>`${part}${part}`).join('')}`;
|
|
318
|
-
if (/^#[0-9a-f]{6}$/.test(trimmed)) return trimmed;
|
|
319
|
-
const rgb = /^rgba?\(\s*(\d+)\s*,\s*(\d+)\s*,\s*(\d+)/.exec(trimmed);
|
|
320
|
-
if (!rgb) return null;
|
|
321
|
-
const channels = rgb.slice(1, 4).map(Number);
|
|
322
|
-
if (channels.some((channel)=>channel < 0 || channel > 255)) return null;
|
|
323
|
-
return `#${channels.map((channel)=>channel.toString(16).padStart(2, '0')).join('')}`;
|
|
324
|
-
}
|
|
325
|
-
function normalizeDocumentTableVerticalAlign(value) {
|
|
326
|
-
if ('top' === value || 'middle' === value || 'bottom' === value) return value;
|
|
327
|
-
if ('center' === value) return 'middle';
|
|
328
|
-
return null;
|
|
329
|
-
}
|
|
330
|
-
function normalizeDocumentTableBorderStyle(value) {
|
|
331
|
-
if ('solid' === value || 'dashed' === value || 'dotted' === value || 'double' === value || 'none' === value) return value;
|
|
332
|
-
return null;
|
|
333
|
-
}
|
|
334
|
-
function normalizeDocumentTableBorderWidth(value) {
|
|
335
|
-
const width = 'number' == typeof value ? value : Number.parseFloat(String(value ?? '').replace(/px$/i, ''));
|
|
336
|
-
if (!Number.isFinite(width) || width < 0 || width > 6) return null;
|
|
337
|
-
return Math.round(2 * width) / 2;
|
|
338
|
-
}
|
|
339
|
-
const DocumentTableRow = TableRow.extend({
|
|
340
|
-
addAttributes () {
|
|
341
|
-
return {
|
|
342
|
-
...this.parent?.() ?? {},
|
|
343
|
-
cantSplit: booleanRowAttribute('cantSplit', 'officeCantSplit', 'data-office-cant-split'),
|
|
344
|
-
repeatHeader: booleanRowAttribute('repeatHeader', 'officeRepeatHeader', 'data-office-repeat-header'),
|
|
345
|
-
rowHeight: {
|
|
346
|
-
default: null,
|
|
347
|
-
parseHTML: (element)=>normalizeDocumentTableRowHeight(element.dataset.officeRowHeight || element.style.height),
|
|
348
|
-
renderHTML: (attributes)=>{
|
|
349
|
-
const height = normalizeDocumentTableRowHeight(attributes.rowHeight);
|
|
350
|
-
return null === height ? {} : {
|
|
351
|
-
'data-office-row-height': String(height),
|
|
352
|
-
style: `height: ${height}px`
|
|
353
|
-
};
|
|
354
|
-
}
|
|
355
|
-
},
|
|
356
|
-
rowHeightRule: {
|
|
357
|
-
default: null,
|
|
358
|
-
parseHTML: (element)=>normalizeDocumentTableRowHeightRule(element.dataset.officeRowHeightRule),
|
|
359
|
-
renderHTML: (attributes)=>{
|
|
360
|
-
const rule = normalizeDocumentTableRowHeightRule(attributes.rowHeightRule);
|
|
361
|
-
return null === rule ? {} : {
|
|
362
|
-
'data-office-row-height-rule': rule
|
|
363
|
-
};
|
|
364
|
-
}
|
|
365
|
-
}
|
|
366
|
-
};
|
|
367
|
-
},
|
|
368
|
-
addCommands () {
|
|
369
|
-
return {
|
|
370
|
-
...this.parent?.() ?? {},
|
|
371
|
-
setDocumentTableRowOptions: (options, commandOptions = {})=>({ chain, editor })=>{
|
|
372
|
-
if (!editor.isActive('table')) return false;
|
|
373
|
-
let commandChain = chain();
|
|
374
|
-
if (false !== commandOptions.restoreFocus) commandChain = commandChain.focus();
|
|
375
|
-
return commandChain.updateAttributes('tableRow', {
|
|
376
|
-
cantSplit: Boolean(options.cantSplit),
|
|
377
|
-
repeatHeader: Boolean(options.repeatHeader)
|
|
378
|
-
}).run();
|
|
379
|
-
}
|
|
380
|
-
};
|
|
381
|
-
}
|
|
382
|
-
});
|
|
383
|
-
function documentTableRowOptions(editor) {
|
|
384
|
-
const attributes = editor.getAttributes('tableRow');
|
|
385
|
-
return {
|
|
386
|
-
cantSplit: directBoolean(attributes.cantSplit) ?? false,
|
|
387
|
-
repeatHeader: directBoolean(attributes.repeatHeader) ?? editor.isActive('tableHeader')
|
|
388
|
-
};
|
|
389
|
-
}
|
|
390
|
-
function canSetDocumentTableRowRepeatHeader(editor) {
|
|
391
|
-
const resolved = editor.state.selection.$from;
|
|
392
|
-
for(let depth = resolved.depth; depth > 0; depth -= 1){
|
|
393
|
-
if ('tableRow' !== resolved.node(depth).type.name) continue;
|
|
394
|
-
const tableDepth = depth - 1;
|
|
395
|
-
const table = resolved.node(tableDepth);
|
|
396
|
-
if ('table' !== table.type.name) break;
|
|
397
|
-
let leadingHeaderCount = 0;
|
|
398
|
-
for(let index = 0; index < table.childCount; index += 1){
|
|
399
|
-
if (!documentTableRowRepeats(table.child(index))) break;
|
|
400
|
-
leadingHeaderCount += 1;
|
|
401
|
-
}
|
|
402
|
-
return resolved.index(tableDepth) <= leadingHeaderCount;
|
|
403
|
-
}
|
|
404
|
-
return false;
|
|
405
|
-
}
|
|
406
|
-
function documentTableRowRepeats(node) {
|
|
407
|
-
const explicit = directBoolean(node.attrs.repeatHeader);
|
|
408
|
-
if (null !== explicit) return explicit;
|
|
409
|
-
if (0 === node.childCount) return false;
|
|
410
|
-
for(let index = 0; index < node.childCount; index += 1)if ('tableHeader' !== node.child(index).type.name) return false;
|
|
411
|
-
return true;
|
|
412
|
-
}
|
|
413
|
-
function documentTableRowCantSplit(node) {
|
|
414
|
-
return directBoolean(node.attrs.cantSplit) ?? false;
|
|
415
|
-
}
|
|
416
|
-
function documentTableRowHeight(attributes) {
|
|
417
|
-
const height = normalizeDocumentTableRowHeight(attributes.rowHeight);
|
|
418
|
-
return {
|
|
419
|
-
height,
|
|
420
|
-
rule: null === height ? null : normalizeDocumentTableRowHeightRule(attributes.rowHeightRule) ?? 'atLeast'
|
|
421
|
-
};
|
|
422
|
-
}
|
|
423
|
-
function normalizeDocumentTableRowHeight(value) {
|
|
424
|
-
const height = Number.parseFloat(String(value ?? '').replace(/px$/i, ''));
|
|
425
|
-
return Number.isFinite(height) && height > 0 ? Math.round(100 * height) / 100 : null;
|
|
426
|
-
}
|
|
427
|
-
function normalizeDocumentTableRowHeightRule(value) {
|
|
428
|
-
return 'exact' === value || 'atLeast' === value ? value : null;
|
|
429
|
-
}
|
|
430
|
-
function booleanRowAttribute(modelKey, datasetKey, htmlName) {
|
|
431
|
-
return {
|
|
432
|
-
default: null,
|
|
433
|
-
parseHTML: (element)=>directBoolean(element.dataset[datasetKey]),
|
|
434
|
-
renderHTML: (attributes)=>{
|
|
435
|
-
const value = directBoolean(attributes[modelKey]);
|
|
436
|
-
return null === value ? {} : {
|
|
437
|
-
[htmlName]: String(value)
|
|
438
|
-
};
|
|
439
|
-
}
|
|
440
|
-
};
|
|
441
|
-
}
|
|
442
|
-
function directBoolean(value) {
|
|
443
|
-
if (true === value || 'true' === value || '1' === value) return true;
|
|
444
|
-
if (false === value || 'false' === value || '0' === value) return false;
|
|
445
|
-
return null;
|
|
446
|
-
}
|
|
447
|
-
const DEFAULT_COLUMN_WIDTH = 120;
|
|
448
|
-
const DEFAULT_ROW_HEIGHT = 36;
|
|
449
|
-
const MIN_COLUMN_WIDTH = 25;
|
|
450
|
-
const MIN_ROW_HEIGHT = 12;
|
|
451
|
-
const MAX_TABLE_DIMENSION = 4000;
|
|
452
|
-
class WorkDocumentTableView extends TableView {
|
|
453
|
-
constructor(node, cellMinWidth, view){
|
|
454
|
-
super(node, cellMinWidth, view);
|
|
455
|
-
this.syncLayout(node);
|
|
456
|
-
}
|
|
457
|
-
update(node) {
|
|
458
|
-
const updated = super.update(node);
|
|
459
|
-
if (updated) this.syncLayout(node);
|
|
460
|
-
return updated;
|
|
461
|
-
}
|
|
462
|
-
syncLayout(node) {
|
|
463
|
-
const mode = normalizeDocumentTableLayoutMode(node.attrs.layoutMode);
|
|
464
|
-
this.table.dataset.officeTableLayout = mode;
|
|
465
|
-
if ('window' === mode) {
|
|
466
|
-
this.clearStaleColumnWidths();
|
|
467
|
-
this.table.style.width = '100%';
|
|
468
|
-
} else if ('contents' === mode) {
|
|
469
|
-
this.clearStaleColumnWidths();
|
|
470
|
-
this.table.style.width = '';
|
|
471
|
-
}
|
|
472
|
-
}
|
|
473
|
-
clearStaleColumnWidths() {
|
|
474
|
-
for (const column of Array.from(this.colgroup.children))if (column instanceof HTMLElement) {
|
|
475
|
-
column.style.removeProperty('width');
|
|
476
|
-
column.style.setProperty('min-width', `${this.cellMinWidth}px`);
|
|
477
|
-
}
|
|
478
|
-
}
|
|
479
|
-
}
|
|
480
|
-
const DocumentTable = Table.extend({
|
|
481
|
-
addAttributes () {
|
|
482
|
-
return {
|
|
483
|
-
...this.parent?.() ?? {},
|
|
484
|
-
layoutMode: {
|
|
485
|
-
default: 'window',
|
|
486
|
-
parseHTML: (element)=>normalizeDocumentTableLayoutMode(element.dataset.officeTableLayout),
|
|
487
|
-
renderHTML: (attributes)=>({
|
|
488
|
-
'data-office-table-layout': normalizeDocumentTableLayoutMode(attributes.layoutMode)
|
|
489
|
-
})
|
|
490
|
-
}
|
|
491
|
-
};
|
|
492
|
-
}
|
|
493
|
-
}).configure({
|
|
494
|
-
resizable: true,
|
|
495
|
-
allowTableNodeSelection: true,
|
|
496
|
-
View: WorkDocumentTableView
|
|
497
|
-
});
|
|
498
|
-
const DocumentTableSizing = Extension.create({
|
|
499
|
-
name: 'documentTableSizing',
|
|
500
|
-
addCommands () {
|
|
501
|
-
return {
|
|
502
|
-
setDocumentTableColumnWidth: (width, renderedColumnWidths)=>(props)=>setSelectedColumnWidth(props, width, renderedColumnWidths),
|
|
503
|
-
setDocumentTableRowHeight: (height, rule = 'atLeast')=>(props)=>setSelectedRowHeight(props, height, rule),
|
|
504
|
-
setDocumentTableLayoutMode: (mode, renderedTableWidth)=>(props)=>setTableLayoutMode(props, mode, renderedTableWidth),
|
|
505
|
-
distributeDocumentTableColumns: (renderedSelectionWidth)=>(props)=>distributeColumns(props, renderedSelectionWidth),
|
|
506
|
-
distributeDocumentTableRows: (renderedSelectionHeight)=>(props)=>distributeRows(props, renderedSelectionHeight)
|
|
507
|
-
};
|
|
508
|
-
},
|
|
509
|
-
addProseMirrorPlugins () {
|
|
510
|
-
return [
|
|
511
|
-
new Plugin({
|
|
512
|
-
appendTransaction: (transactions, _oldState, newState)=>{
|
|
513
|
-
if (!transactions.some((transaction)=>transaction.docChanged)) return null;
|
|
514
|
-
const transaction = newState.tr;
|
|
515
|
-
newState.doc.descendants((node, position)=>{
|
|
516
|
-
if ('table' !== node.type.spec.tableRole) return true;
|
|
517
|
-
if ('window' === normalizeDocumentTableLayoutMode(node.attrs.layoutMode) && tableHasExplicitColumnWidths(node)) transaction.setNodeMarkup(position, void 0, {
|
|
518
|
-
...node.attrs,
|
|
519
|
-
layoutMode: 'fixed'
|
|
520
|
-
});
|
|
521
|
-
return false;
|
|
522
|
-
});
|
|
523
|
-
return transaction.docChanged ? transaction : null;
|
|
524
|
-
}
|
|
525
|
-
})
|
|
526
|
-
];
|
|
527
|
-
}
|
|
528
|
-
});
|
|
529
|
-
function documentTableSizing(state) {
|
|
530
|
-
const context = tableSizingContext(state);
|
|
531
|
-
if (!context) return null;
|
|
532
|
-
const columns = numberRange(context.left, context.right);
|
|
533
|
-
const rows = numberRange(context.top, context.bottom);
|
|
534
|
-
const widths = tableColumnWidths(context.table, context.map).filter((_width, index)=>columns.includes(index));
|
|
535
|
-
const rowSizes = tableRowSizes(context.table).filter((_size, index)=>rows.includes(index));
|
|
536
|
-
return {
|
|
537
|
-
columnWidth: commonPositiveValue(widths),
|
|
538
|
-
rowHeight: commonNullableValue(rowSizes.map(({ height })=>height)),
|
|
539
|
-
rowHeightRule: commonNullableValue(rowSizes.map(({ rule })=>rule)),
|
|
540
|
-
layoutMode: normalizeDocumentTableLayoutMode(context.table.attrs.layoutMode),
|
|
541
|
-
selectedColumnCount: columns.length,
|
|
542
|
-
selectedRowCount: rows.length
|
|
543
|
-
};
|
|
544
|
-
}
|
|
545
|
-
function normalizeDocumentTableLayoutMode(value) {
|
|
546
|
-
return 'contents' === value || 'fixed' === value ? value : 'window';
|
|
547
|
-
}
|
|
548
|
-
function setSelectedColumnWidth({ dispatch, state }, width, renderedColumnWidths) {
|
|
549
|
-
const normalized = normalizedDimension(width, MIN_COLUMN_WIDTH, MAX_TABLE_DIMENSION);
|
|
550
|
-
const context = tableSizingContext(state);
|
|
551
|
-
if (!context || null === normalized) return false;
|
|
552
|
-
if (!dispatch) return true;
|
|
553
|
-
const transaction = state.tr;
|
|
554
|
-
const preservedWidths = normalizeRenderedDimensions(renderedColumnWidths, context.map.width, MIN_COLUMN_WIDTH);
|
|
555
|
-
if (preservedWidths) {
|
|
556
|
-
for(let column = context.left; column < context.right; column += 1)preservedWidths[column] = normalized;
|
|
557
|
-
setPhysicalColumnWidths(transaction, context, preservedWidths, 0);
|
|
558
|
-
} else setPhysicalColumnWidths(transaction, context, numberRange(context.left, context.right).map(()=>normalized), context.left);
|
|
559
|
-
setTableLayoutAttribute(transaction, context, 'fixed');
|
|
560
|
-
dispatchTableSizingTransaction(dispatch, transaction, context, state);
|
|
561
|
-
return true;
|
|
562
|
-
}
|
|
563
|
-
function setSelectedRowHeight({ dispatch, state }, height, rule) {
|
|
564
|
-
const normalized = null === height ? null : normalizedDimension(height, MIN_ROW_HEIGHT, MAX_TABLE_DIMENSION);
|
|
565
|
-
const context = tableSizingContext(state);
|
|
566
|
-
if (!context || null !== height && null === normalized) return false;
|
|
567
|
-
if ('atLeast' !== rule && 'exact' !== rule) return false;
|
|
568
|
-
if (!dispatch) return true;
|
|
569
|
-
const transaction = state.tr;
|
|
570
|
-
setPhysicalRowHeights(transaction, context, numberRange(context.top, context.bottom), normalized, rule);
|
|
571
|
-
dispatchTableSizingTransaction(dispatch, transaction, context, state);
|
|
572
|
-
return true;
|
|
573
|
-
}
|
|
574
|
-
function setTableLayoutMode({ dispatch, state }, requestedMode, renderedTableWidth) {
|
|
575
|
-
if ('window' !== requestedMode && 'contents' !== requestedMode && 'fixed' !== requestedMode) return false;
|
|
576
|
-
const context = tableSizingContext(state);
|
|
577
|
-
if (!context) return false;
|
|
578
|
-
if (!dispatch) return true;
|
|
579
|
-
const transaction = state.tr;
|
|
580
|
-
setTableLayoutAttribute(transaction, context, requestedMode);
|
|
581
|
-
if ('fixed' === requestedMode) {
|
|
582
|
-
const existing = tableColumnWidths(context.table, context.map);
|
|
583
|
-
const total = distributionTotal(existing, renderedTableWidth, DEFAULT_COLUMN_WIDTH);
|
|
584
|
-
setPhysicalColumnWidths(transaction, context, equalDimensions(total, context.map.width, MIN_COLUMN_WIDTH), 0);
|
|
585
|
-
} else clearPhysicalColumnWidths(transaction, context);
|
|
586
|
-
dispatchTableSizingTransaction(dispatch, transaction, context, state);
|
|
587
|
-
return true;
|
|
588
|
-
}
|
|
589
|
-
function distributeColumns({ dispatch, state }, renderedSelectionWidth) {
|
|
590
|
-
const context = tableSizingContext(state);
|
|
591
|
-
if (!context) return false;
|
|
592
|
-
const selected = numberRange(context.left, context.right);
|
|
593
|
-
const columns = selected.length > 1 ? selected : numberRange(0, context.map.width);
|
|
594
|
-
if (columns.length < 2) return false;
|
|
595
|
-
if (!dispatch) return true;
|
|
596
|
-
const allWidths = tableColumnWidths(context.table, context.map);
|
|
597
|
-
const existing = columns.map((column)=>allWidths[column] ?? null);
|
|
598
|
-
const total = distributionTotal(existing, renderedSelectionWidth, DEFAULT_COLUMN_WIDTH);
|
|
599
|
-
const transaction = state.tr;
|
|
600
|
-
setPhysicalColumnWidths(transaction, context, equalDimensions(total, columns.length, MIN_COLUMN_WIDTH), columns[0] ?? 0);
|
|
601
|
-
setTableLayoutAttribute(transaction, context, 'fixed');
|
|
602
|
-
dispatchTableSizingTransaction(dispatch, transaction, context, state);
|
|
603
|
-
return true;
|
|
604
|
-
}
|
|
605
|
-
function distributeRows({ dispatch, state }, renderedSelectionHeight) {
|
|
606
|
-
const context = tableSizingContext(state);
|
|
607
|
-
if (!context) return false;
|
|
608
|
-
const selected = numberRange(context.top, context.bottom);
|
|
609
|
-
const rows = selected.length > 1 ? selected : numberRange(0, context.map.height);
|
|
610
|
-
if (rows.length < 2) return false;
|
|
611
|
-
if (!dispatch) return true;
|
|
612
|
-
const allSizes = tableRowSizes(context.table);
|
|
613
|
-
const existing = rows.map((row)=>allSizes[row]?.height ?? null);
|
|
614
|
-
const total = distributionTotal(existing, renderedSelectionHeight, DEFAULT_ROW_HEIGHT);
|
|
615
|
-
const [height] = equalDimensions(total, rows.length, MIN_ROW_HEIGHT);
|
|
616
|
-
const transaction = state.tr;
|
|
617
|
-
setPhysicalRowHeights(transaction, context, rows, height ?? DEFAULT_ROW_HEIGHT, 'atLeast');
|
|
618
|
-
dispatchTableSizingTransaction(dispatch, transaction, context, state);
|
|
619
|
-
return true;
|
|
620
|
-
}
|
|
621
|
-
function tableSizingContext(state) {
|
|
622
|
-
if (state.selection instanceof NodeSelection && 'table' === state.selection.node.type.spec.tableRole) {
|
|
623
|
-
const table = state.selection.node;
|
|
624
|
-
const map = TableMap.get(table);
|
|
625
|
-
return {
|
|
626
|
-
table,
|
|
627
|
-
tableStart: state.selection.from + 1,
|
|
628
|
-
map,
|
|
629
|
-
left: 0,
|
|
630
|
-
right: map.width,
|
|
631
|
-
top: 0,
|
|
632
|
-
bottom: map.height
|
|
633
|
-
};
|
|
634
|
-
}
|
|
635
|
-
if (!isInTable(state)) return null;
|
|
636
|
-
const rectangle = selectedRect(state);
|
|
637
|
-
return {
|
|
638
|
-
table: rectangle.table,
|
|
639
|
-
tableStart: rectangle.tableStart,
|
|
640
|
-
map: rectangle.map,
|
|
641
|
-
left: rectangle.left,
|
|
642
|
-
right: rectangle.right,
|
|
643
|
-
top: rectangle.top,
|
|
644
|
-
bottom: rectangle.bottom
|
|
645
|
-
};
|
|
646
|
-
}
|
|
647
|
-
function dispatchTableSizingTransaction(dispatch, transaction, context, state) {
|
|
648
|
-
if (!transaction.docChanged) return;
|
|
649
|
-
if (state.selection instanceof NodeSelection && 'table' === state.selection.node.type.spec.tableRole) {
|
|
650
|
-
const tablePosition = context.tableStart - 1;
|
|
651
|
-
if (transaction.doc.nodeAt(tablePosition)?.type.spec.tableRole === 'table') transaction.setSelection(NodeSelection.create(transaction.doc, tablePosition));
|
|
652
|
-
}
|
|
653
|
-
dispatch(transaction.scrollIntoView());
|
|
654
|
-
}
|
|
655
|
-
function setPhysicalColumnWidths(transaction, context, widths, startColumn) {
|
|
656
|
-
const touched = new Set();
|
|
657
|
-
widths.forEach((width, widthIndex)=>{
|
|
658
|
-
const column = startColumn + widthIndex;
|
|
659
|
-
if (column < 0 || column >= context.map.width) return;
|
|
660
|
-
for(let row = 0; row < context.map.height; row += 1){
|
|
661
|
-
const relativePosition = context.map.map[row * context.map.width + column];
|
|
662
|
-
if (void 0 === relativePosition) continue;
|
|
663
|
-
const cell = context.table.nodeAt(relativePosition);
|
|
664
|
-
if (!cell) continue;
|
|
665
|
-
const widthIndexInCell = column - context.map.colCount(relativePosition);
|
|
666
|
-
const key = `${relativePosition}:${widthIndexInCell}`;
|
|
667
|
-
if (touched.has(key)) continue;
|
|
668
|
-
touched.add(key);
|
|
669
|
-
const documentPosition = context.tableStart + relativePosition;
|
|
670
|
-
const current = transaction.doc.nodeAt(documentPosition);
|
|
671
|
-
if (!current) continue;
|
|
672
|
-
const colwidth = Array.isArray(current.attrs.colwidth) ? [
|
|
673
|
-
...current.attrs.colwidth
|
|
674
|
-
] : Array.from({
|
|
675
|
-
length: Number(current.attrs.colspan ?? 1)
|
|
676
|
-
}, ()=>0);
|
|
677
|
-
colwidth[widthIndexInCell] = width;
|
|
678
|
-
transaction.setNodeMarkup(documentPosition, void 0, {
|
|
679
|
-
...current.attrs,
|
|
680
|
-
colwidth
|
|
681
|
-
});
|
|
682
|
-
}
|
|
683
|
-
});
|
|
684
|
-
}
|
|
685
|
-
function clearPhysicalColumnWidths(transaction, context) {
|
|
686
|
-
context.table.descendants((node, offset)=>{
|
|
687
|
-
if (!work_document_table_sizing_isTableCell(node)) return true;
|
|
688
|
-
const position = context.tableStart + offset;
|
|
689
|
-
const current = transaction.doc.nodeAt(position);
|
|
690
|
-
if (current?.attrs.colwidth) transaction.setNodeMarkup(position, void 0, {
|
|
691
|
-
...current.attrs,
|
|
692
|
-
colwidth: null
|
|
693
|
-
});
|
|
694
|
-
return false;
|
|
695
|
-
});
|
|
696
|
-
}
|
|
697
|
-
function setPhysicalRowHeights(transaction, context, rows, height, rule) {
|
|
698
|
-
const selectedRows = new Set(rows);
|
|
699
|
-
context.table.forEach((_row, offset, index)=>{
|
|
700
|
-
if (!selectedRows.has(index)) return;
|
|
701
|
-
const position = context.tableStart + offset;
|
|
702
|
-
const current = transaction.doc.nodeAt(position);
|
|
703
|
-
if (!current) return;
|
|
704
|
-
transaction.setNodeMarkup(position, void 0, {
|
|
705
|
-
...current.attrs,
|
|
706
|
-
rowHeight: height,
|
|
707
|
-
rowHeightRule: null === height ? null : rule
|
|
708
|
-
});
|
|
709
|
-
});
|
|
710
|
-
}
|
|
711
|
-
function setTableLayoutAttribute(transaction, context, layoutMode) {
|
|
712
|
-
const position = context.tableStart - 1;
|
|
713
|
-
const table = transaction.doc.nodeAt(position);
|
|
714
|
-
if (!table) return;
|
|
715
|
-
transaction.setNodeMarkup(position, void 0, {
|
|
716
|
-
...table.attrs,
|
|
717
|
-
layoutMode
|
|
718
|
-
});
|
|
719
|
-
}
|
|
720
|
-
function tableColumnWidths(table, map) {
|
|
721
|
-
return Array.from({
|
|
722
|
-
length: map.width
|
|
723
|
-
}, (_unused, column)=>{
|
|
724
|
-
for(let row = 0; row < map.height; row += 1){
|
|
725
|
-
const position = map.map[row * map.width + column];
|
|
726
|
-
if (void 0 === position) continue;
|
|
727
|
-
const cell = table.nodeAt(position);
|
|
728
|
-
const index = column - map.colCount(position);
|
|
729
|
-
const value = Array.isArray(cell?.attrs.colwidth) ? Number(cell.attrs.colwidth[index]) : 0;
|
|
730
|
-
if (Number.isFinite(value) && value > 0) return value;
|
|
731
|
-
}
|
|
732
|
-
return null;
|
|
733
|
-
});
|
|
734
|
-
}
|
|
735
|
-
function tableRowSizes(table) {
|
|
736
|
-
const sizes = [];
|
|
737
|
-
table.forEach((row)=>{
|
|
738
|
-
sizes.push(documentTableRowHeight(row.attrs));
|
|
739
|
-
});
|
|
740
|
-
return sizes;
|
|
741
|
-
}
|
|
742
|
-
function tableHasExplicitColumnWidths(table) {
|
|
743
|
-
let found = false;
|
|
744
|
-
table.descendants((node)=>{
|
|
745
|
-
if (!work_document_table_sizing_isTableCell(node)) return true;
|
|
746
|
-
if (Array.isArray(node.attrs.colwidth) && node.attrs.colwidth.some((width)=>Number(width) > 0)) found = true;
|
|
747
|
-
return !found;
|
|
748
|
-
});
|
|
749
|
-
return found;
|
|
750
|
-
}
|
|
751
|
-
function work_document_table_sizing_isTableCell(node) {
|
|
752
|
-
return 'cell' === node.type.spec.tableRole || 'header_cell' === node.type.spec.tableRole;
|
|
753
|
-
}
|
|
754
|
-
function normalizedDimension(value, minimum, maximum) {
|
|
755
|
-
if (!Number.isFinite(value) || value < minimum || value > maximum) return null;
|
|
756
|
-
return Math.round(100 * value) / 100;
|
|
757
|
-
}
|
|
758
|
-
function normalizeRenderedDimensions(values, expectedCount, minimum) {
|
|
759
|
-
if (!values || values.length !== expectedCount) return null;
|
|
760
|
-
const normalized = values.map((value)=>normalizedDimension(value, minimum, MAX_TABLE_DIMENSION));
|
|
761
|
-
return normalized.every((value)=>null !== value) ? normalized : null;
|
|
762
|
-
}
|
|
763
|
-
function numberRange(start, end) {
|
|
764
|
-
return Array.from({
|
|
765
|
-
length: Math.max(0, end - start)
|
|
766
|
-
}, (_unused, index)=>start + index);
|
|
767
|
-
}
|
|
768
|
-
function distributionTotal(existing, rendered, fallback) {
|
|
769
|
-
if (Number.isFinite(rendered) && Number(rendered) > 0) return Number(rendered);
|
|
770
|
-
if (existing.every((value)=>null !== value && value > 0)) return existing.reduce((sum, value)=>sum + Number(value), 0);
|
|
771
|
-
return fallback * existing.length;
|
|
772
|
-
}
|
|
773
|
-
function equalDimensions(total, count, minimum) {
|
|
774
|
-
const size = Math.max(minimum, Math.round(total / count * 100) / 100);
|
|
775
|
-
return Array.from({
|
|
776
|
-
length: count
|
|
777
|
-
}, ()=>size);
|
|
778
|
-
}
|
|
779
|
-
function commonPositiveValue(values) {
|
|
780
|
-
if (!values.length || values.some((value)=>null === value || value <= 0)) return null;
|
|
781
|
-
return values.every((value)=>value === values[0]) ? values[0] : null;
|
|
782
|
-
}
|
|
783
|
-
function commonNullableValue(values) {
|
|
784
|
-
if (!values.length || values.some((value)=>null === value)) return null;
|
|
785
|
-
return values.every((value)=>value === values[0]) ? values[0] : null;
|
|
786
|
-
}
|
|
787
|
-
export { DEFAULT_DOCUMENT_TABLE_CELL_FORMAT, DOCUMENT_TABLE_STYLE_OPTIONS, DocumentTable, DocumentTableCell, DocumentTableFormatting, DocumentTableHeader, DocumentTableRow, DocumentTableSizing, activeDocumentTableStyle, canSetDocumentTableRowRepeatHeader, documentTableCellFormat, documentTableHorizontalAlignment, documentTableRowCantSplit, documentTableRowOptions, documentTableRowRepeats, documentTableSizing, normalizeDocumentTableBorderStyle, normalizeDocumentTableBorderWidth, normalizeDocumentTableLayoutMode, normalizeDocumentTableRowHeightRule, normalizeDocumentTableVerticalAlign, normalizeTableColor };
|