@harbour-enterprises/superdoc 1.5.0-next.5 → 1.5.0-next.7
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/dist/chunks/{PdfViewer-s90Ubj4h.es.js → PdfViewer-ClST5VR6.es.js} +2 -2
- package/dist/chunks/{PdfViewer-BsNt5K_V.cjs → PdfViewer-Cli6IR-X.cjs} +2 -2
- package/dist/chunks/{SuperConverter--XoKPr84.cjs → SuperConverter-CIjArITT.cjs} +608 -36
- package/dist/chunks/{SuperConverter-BYBgTS6T.es.js → SuperConverter-S5AfMnkn.es.js} +608 -36
- package/dist/chunks/{index-u4_Ee95y.es.js → index-7ebfCUN0.es.js} +11 -4
- package/dist/chunks/{index-H9yQJDe_.cjs → index-CbbEjpJ0.cjs} +4 -4
- package/dist/chunks/{index-hAbdauPd.cjs → index-LpMObyDy.cjs} +11 -4
- package/dist/chunks/{index-ARobn9PY.es.js → index-bw_yQ0EP.es.js} +4 -4
- package/dist/super-editor/converter.cjs +1 -1
- package/dist/super-editor/converter.es.js +1 -1
- package/dist/super-editor.cjs +2 -2
- package/dist/super-editor.es.js +3 -3
- package/dist/superdoc.cjs +3 -3
- package/dist/superdoc.es.js +3 -3
- package/dist/superdoc.umd.js +617 -38
- package/dist/superdoc.umd.js.map +1 -1
- package/package.json +3 -3
|
@@ -3643,6 +3643,11 @@ const DEFAULT_DOCX_DEFS = {
|
|
|
3643
3643
|
"xmlns:v": "urn:schemas-microsoft-com:vml",
|
|
3644
3644
|
"xmlns:wp14": "http://schemas.microsoft.com/office/word/2010/wordprocessingDrawing",
|
|
3645
3645
|
"xmlns:wp": "http://schemas.openxmlformats.org/drawingml/2006/wordprocessingDrawing",
|
|
3646
|
+
"xmlns:a": "http://schemas.openxmlformats.org/drawingml/2006/main",
|
|
3647
|
+
"xmlns:pic": "http://schemas.openxmlformats.org/drawingml/2006/picture",
|
|
3648
|
+
"xmlns:c": "http://schemas.openxmlformats.org/drawingml/2006/chart",
|
|
3649
|
+
"xmlns:dgm": "http://schemas.openxmlformats.org/drawingml/2006/diagram",
|
|
3650
|
+
"xmlns:lc": "http://schemas.openxmlformats.org/drawingml/2006/lockedCanvas",
|
|
3646
3651
|
"xmlns:w10": "urn:schemas-microsoft-com:office:word",
|
|
3647
3652
|
"xmlns:w": "http://schemas.openxmlformats.org/wordprocessingml/2006/main",
|
|
3648
3653
|
"xmlns:w14": "http://schemas.microsoft.com/office/word/2010/wordml",
|
|
@@ -10087,6 +10092,11 @@ const SD_NODE_NAME$g = "tableRow";
|
|
|
10087
10092
|
const validXmlAttributes$9 = ["w:rsidDel", "w:rsidR", "w:rsidRPr", "w:rsidTr", "w14:paraId", "w14:textId"].map(
|
|
10088
10093
|
(xmlName) => createAttributeHandler(xmlName)
|
|
10089
10094
|
);
|
|
10095
|
+
const getColspan$1 = (cell) => {
|
|
10096
|
+
const rawColspan = cell?.attrs?.colspan;
|
|
10097
|
+
const numericColspan = typeof rawColspan === "string" ? parseInt(rawColspan, 10) : rawColspan;
|
|
10098
|
+
return Number.isFinite(numericColspan) && numericColspan > 0 ? numericColspan : 1;
|
|
10099
|
+
};
|
|
10090
10100
|
const encode$v = (params, encodedAttrs) => {
|
|
10091
10101
|
const { row } = params.extraParams;
|
|
10092
10102
|
let tableRowProperties = {};
|
|
@@ -10219,7 +10229,27 @@ const decode$x = (params, decodedAttrs) => {
|
|
|
10219
10229
|
}
|
|
10220
10230
|
return cell;
|
|
10221
10231
|
});
|
|
10222
|
-
|
|
10232
|
+
let trimmedContent = sanitizedCells.filter((_2, index2) => !isPlaceholderCell(trimmedSlice[index2]));
|
|
10233
|
+
const preferTableGrid = params.extraParams?.preferTableGrid === true;
|
|
10234
|
+
const totalColumns = params.extraParams?.totalColumns;
|
|
10235
|
+
if (preferTableGrid && typeof totalColumns === "number" && Number.isFinite(totalColumns) && totalColumns > 0) {
|
|
10236
|
+
const rawGridBefore = node.attrs?.tableRowProperties?.gridBefore;
|
|
10237
|
+
const numericGridBefore = typeof rawGridBefore === "string" ? parseInt(rawGridBefore, 10) : rawGridBefore;
|
|
10238
|
+
const safeGridBefore = Number.isFinite(numericGridBefore) && numericGridBefore > 0 ? numericGridBefore : 0;
|
|
10239
|
+
const effectiveGridBefore = leadingPlaceholders > 0 ? leadingPlaceholders : safeGridBefore;
|
|
10240
|
+
const availableColumns = Math.max(totalColumns - effectiveGridBefore, 0);
|
|
10241
|
+
let usedColumns = 0;
|
|
10242
|
+
const constrainedCells = [];
|
|
10243
|
+
for (const cell of trimmedContent) {
|
|
10244
|
+
const colspan = getColspan$1(cell);
|
|
10245
|
+
if (usedColumns + colspan > availableColumns) {
|
|
10246
|
+
break;
|
|
10247
|
+
}
|
|
10248
|
+
constrainedCells.push(cell);
|
|
10249
|
+
usedColumns += colspan;
|
|
10250
|
+
}
|
|
10251
|
+
trimmedContent = constrainedCells;
|
|
10252
|
+
}
|
|
10223
10253
|
const translateParams = {
|
|
10224
10254
|
...params,
|
|
10225
10255
|
node: { ...node, content: trimmedContent }
|
|
@@ -19241,9 +19271,9 @@ function handleImageNode(node, params, isAnchor) {
|
|
|
19241
19271
|
if (!blip) {
|
|
19242
19272
|
return null;
|
|
19243
19273
|
}
|
|
19244
|
-
const stretch = blipFill?.elements
|
|
19245
|
-
const fillRect = stretch?.elements
|
|
19246
|
-
const srcRect = blipFill?.elements
|
|
19274
|
+
const stretch = blipFill?.elements?.find((el) => el.name === "a:stretch");
|
|
19275
|
+
const fillRect = stretch?.elements?.find((el) => el.name === "a:fillRect");
|
|
19276
|
+
const srcRect = blipFill?.elements?.find((el) => el.name === "a:srcRect");
|
|
19247
19277
|
const srcRectAttrs = srcRect?.attributes || {};
|
|
19248
19278
|
const srcRectHasNegativeValues = ["l", "t", "r", "b"].some((attr) => {
|
|
19249
19279
|
const val = srcRectAttrs[attr];
|
|
@@ -25964,6 +25994,53 @@ const config$d = {
|
|
|
25964
25994
|
attributes: validXmlAttributes$5
|
|
25965
25995
|
};
|
|
25966
25996
|
const translator$s = NodeTranslator.from(config$d);
|
|
25997
|
+
const getColspan = (cell) => {
|
|
25998
|
+
const rawColspan = cell?.attrs?.colspan;
|
|
25999
|
+
const numericColspan = typeof rawColspan === "string" ? parseInt(rawColspan, 10) : rawColspan;
|
|
26000
|
+
return Number.isFinite(numericColspan) && numericColspan > 0 ? numericColspan : 1;
|
|
26001
|
+
};
|
|
26002
|
+
const resolveGridBefore = (row) => {
|
|
26003
|
+
const rawGridBefore = row?.attrs?.tableRowProperties?.gridBefore ?? row?.attrs?.gridBefore;
|
|
26004
|
+
const numericGridBefore = typeof rawGridBefore === "string" ? parseInt(rawGridBefore, 10) : rawGridBefore;
|
|
26005
|
+
if (!Number.isFinite(numericGridBefore) || numericGridBefore <= 0) return 0;
|
|
26006
|
+
const cells = Array.isArray(row.content) ? row.content : [];
|
|
26007
|
+
let leadingGridBefore = 0;
|
|
26008
|
+
while (leadingGridBefore < cells.length && cells[leadingGridBefore]?.attrs?.__placeholder === "gridBefore") {
|
|
26009
|
+
leadingGridBefore += 1;
|
|
26010
|
+
}
|
|
26011
|
+
return leadingGridBefore > 0 ? 0 : numericGridBefore;
|
|
26012
|
+
};
|
|
26013
|
+
const advanceColumnsForCell = (columnIndex, cell) => columnIndex + getColspan(cell);
|
|
26014
|
+
const getCellStartColumn = (row, targetCell) => {
|
|
26015
|
+
const cells = Array.isArray(row.content) ? row.content : [];
|
|
26016
|
+
let columnIndex = resolveGridBefore(row);
|
|
26017
|
+
for (const cell of cells) {
|
|
26018
|
+
if (cell === targetCell) return columnIndex;
|
|
26019
|
+
columnIndex = advanceColumnsForCell(columnIndex, cell);
|
|
26020
|
+
}
|
|
26021
|
+
return columnIndex;
|
|
26022
|
+
};
|
|
26023
|
+
const findCellCoveringColumn = (row, targetColumn) => {
|
|
26024
|
+
const cells = Array.isArray(row.content) ? row.content : [];
|
|
26025
|
+
let columnIndex = resolveGridBefore(row);
|
|
26026
|
+
for (const cell of cells) {
|
|
26027
|
+
const colspan = getColspan(cell);
|
|
26028
|
+
if (targetColumn >= columnIndex && targetColumn < columnIndex + colspan) {
|
|
26029
|
+
return cell;
|
|
26030
|
+
}
|
|
26031
|
+
columnIndex = advanceColumnsForCell(columnIndex, cell);
|
|
26032
|
+
}
|
|
26033
|
+
return null;
|
|
26034
|
+
};
|
|
26035
|
+
const findInsertionIndexForColumn = (row, targetColumn) => {
|
|
26036
|
+
const cells = Array.isArray(row.content) ? row.content : [];
|
|
26037
|
+
let columnIndex = resolveGridBefore(row);
|
|
26038
|
+
for (let index2 = 0; index2 < cells.length; index2++) {
|
|
26039
|
+
if (columnIndex >= targetColumn) return index2;
|
|
26040
|
+
columnIndex = advanceColumnsForCell(columnIndex, cells[index2]);
|
|
26041
|
+
}
|
|
26042
|
+
return cells.length;
|
|
26043
|
+
};
|
|
25967
26044
|
function preProcessVerticalMergeCells(table, { editorSchema }) {
|
|
25968
26045
|
if (!table || !Array.isArray(table.content)) {
|
|
25969
26046
|
return table;
|
|
@@ -25979,15 +26056,17 @@ function preProcessVerticalMergeCells(table, { editorSchema }) {
|
|
|
25979
26056
|
const cell = row.content[cellIndex];
|
|
25980
26057
|
if (!cell) continue;
|
|
25981
26058
|
const attrs = cell.attrs || {};
|
|
25982
|
-
|
|
25983
|
-
|
|
26059
|
+
const rawRowspan = typeof attrs.rowspan === "string" ? parseInt(attrs.rowspan, 10) : attrs.rowspan;
|
|
26060
|
+
if (!Number.isFinite(rawRowspan) || rawRowspan <= 1) continue;
|
|
26061
|
+
const maxRowspan = Math.min(rawRowspan, rows.length - rowIndex);
|
|
26062
|
+
const startColumn = getCellStartColumn(row, cell);
|
|
25984
26063
|
for (let offset = 1; offset < maxRowspan; offset++) {
|
|
25985
26064
|
const rowToChange = rows[rowIndex + offset];
|
|
25986
26065
|
if (!rowToChange) continue;
|
|
25987
26066
|
if (!Array.isArray(rowToChange.content)) {
|
|
25988
26067
|
rowToChange.content = [];
|
|
25989
26068
|
}
|
|
25990
|
-
const existingCell = rowToChange
|
|
26069
|
+
const existingCell = findCellCoveringColumn(rowToChange, startColumn);
|
|
25991
26070
|
if (existingCell?.attrs?.continueMerge) continue;
|
|
25992
26071
|
const mergedCell = {
|
|
25993
26072
|
type: cell.type,
|
|
@@ -25998,7 +26077,8 @@ function preProcessVerticalMergeCells(table, { editorSchema }) {
|
|
|
25998
26077
|
continueMerge: true
|
|
25999
26078
|
}
|
|
26000
26079
|
};
|
|
26001
|
-
rowToChange
|
|
26080
|
+
const insertionIndex = findInsertionIndexForColumn(rowToChange, startColumn);
|
|
26081
|
+
rowToChange.content.splice(insertionIndex, 0, mergedCell);
|
|
26002
26082
|
}
|
|
26003
26083
|
}
|
|
26004
26084
|
}
|
|
@@ -26150,15 +26230,24 @@ const encode$q = (params) => {
|
|
|
26150
26230
|
const decode$s = (params) => {
|
|
26151
26231
|
const { grid: rawGrid } = params.node.attrs || {};
|
|
26152
26232
|
const grid = Array.isArray(rawGrid) ? rawGrid : [];
|
|
26153
|
-
const { firstRow = {} } = params.extraParams || {};
|
|
26233
|
+
const { firstRow = {}, preferTableGrid = false, totalColumns: requestedColumns } = params.extraParams || {};
|
|
26154
26234
|
const cellNodes = firstRow.content?.filter((n) => n.type === "tableCell") ?? [];
|
|
26155
|
-
|
|
26235
|
+
let colWidthsFromCellNodes = cellNodes.flatMap((cell) => {
|
|
26156
26236
|
const spanCount = Math.max(1, cell?.attrs?.colspan ?? 1);
|
|
26157
26237
|
const colwidth = cell.attrs?.colwidth;
|
|
26158
26238
|
return Array.from({ length: spanCount }).map((_2, span) => Array.isArray(colwidth) ? colwidth[span] : void 0);
|
|
26159
26239
|
});
|
|
26160
26240
|
const columnCountFromCells = colWidthsFromCellNodes.length;
|
|
26161
|
-
const
|
|
26241
|
+
const gridColumnCount = grid.length;
|
|
26242
|
+
let totalColumns = Math.max(columnCountFromCells, gridColumnCount);
|
|
26243
|
+
if (typeof requestedColumns === "number" && Number.isFinite(requestedColumns) && requestedColumns > 0) {
|
|
26244
|
+
totalColumns = requestedColumns;
|
|
26245
|
+
} else if (preferTableGrid && gridColumnCount > 0) {
|
|
26246
|
+
totalColumns = gridColumnCount;
|
|
26247
|
+
}
|
|
26248
|
+
if (colWidthsFromCellNodes.length > totalColumns) {
|
|
26249
|
+
colWidthsFromCellNodes = colWidthsFromCellNodes.slice(0, totalColumns);
|
|
26250
|
+
}
|
|
26162
26251
|
const fallbackColumnWidthTwips = resolveFallbackColumnWidthTwips(params, totalColumns, cellMinWidth);
|
|
26163
26252
|
const elements = [];
|
|
26164
26253
|
const pushColumn = (widthTwips, { enforceMinimum = false } = {}) => {
|
|
@@ -26418,22 +26507,31 @@ const encode$p = (params, encodedAttrs) => {
|
|
|
26418
26507
|
const decode$r = (params, decodedAttrs) => {
|
|
26419
26508
|
params.node = preProcessVerticalMergeCells(params.node, params);
|
|
26420
26509
|
const { node } = params;
|
|
26421
|
-
const
|
|
26510
|
+
const rawGrid = node.attrs?.grid;
|
|
26511
|
+
const grid = Array.isArray(rawGrid) ? rawGrid : [];
|
|
26512
|
+
const preferTableGrid = node.attrs?.userEdited !== true && grid.length > 0;
|
|
26513
|
+
const totalColumns = preferTableGrid ? grid.length : void 0;
|
|
26514
|
+
const extraParams = {
|
|
26515
|
+
...params.extraParams || {},
|
|
26516
|
+
preferTableGrid,
|
|
26517
|
+
totalColumns
|
|
26518
|
+
};
|
|
26519
|
+
const elements = translateChildNodes({ ...params, extraParams });
|
|
26422
26520
|
const firstRow = node.content?.find((n) => n.type === "tableRow");
|
|
26423
|
-
const properties = node.attrs.grid;
|
|
26424
26521
|
const element = translator$c.decode({
|
|
26425
26522
|
...params,
|
|
26426
|
-
node: { ...node, attrs: { ...node.attrs, grid
|
|
26523
|
+
node: { ...node, attrs: { ...node.attrs, grid } },
|
|
26427
26524
|
extraParams: {
|
|
26525
|
+
...extraParams,
|
|
26428
26526
|
firstRow
|
|
26429
26527
|
}
|
|
26430
26528
|
});
|
|
26431
26529
|
if (element) elements.unshift(element);
|
|
26432
26530
|
if (node.attrs?.tableProperties) {
|
|
26433
|
-
const
|
|
26531
|
+
const properties = { ...node.attrs.tableProperties };
|
|
26434
26532
|
const element2 = translator$e.decode({
|
|
26435
26533
|
...params,
|
|
26436
|
-
node: { ...node, attrs: { ...node.attrs, tableProperties:
|
|
26534
|
+
node: { ...node, attrs: { ...node.attrs, tableProperties: properties } }
|
|
26437
26535
|
});
|
|
26438
26536
|
if (element2) elements.unshift(element2);
|
|
26439
26537
|
}
|
|
@@ -30034,7 +30132,7 @@ function buildStyles(styleObject) {
|
|
|
30034
30132
|
}
|
|
30035
30133
|
return style;
|
|
30036
30134
|
}
|
|
30037
|
-
function
|
|
30135
|
+
function handleShapeImageWatermarkImport({ params, pict }) {
|
|
30038
30136
|
const shape = pict.elements?.find((el) => el.name === "v:shape");
|
|
30039
30137
|
if (!shape) return null;
|
|
30040
30138
|
const imagedata = shape.elements?.find((el) => el.name === "v:imagedata");
|
|
@@ -30060,7 +30158,7 @@ function handleShapeImageImport({ params, pict }) {
|
|
|
30060
30158
|
const targetPath = rel.attributes["Target"];
|
|
30061
30159
|
const normalizedPath = normalizeTargetPath(targetPath);
|
|
30062
30160
|
const style = shapeAttrs.style || "";
|
|
30063
|
-
const styleObj = parseVmlStyle(style);
|
|
30161
|
+
const styleObj = parseVmlStyle$1(style);
|
|
30064
30162
|
const width = styleObj.width || "100px";
|
|
30065
30163
|
const height = styleObj.height || "100px";
|
|
30066
30164
|
const position = {
|
|
@@ -30106,12 +30204,12 @@ function handleShapeImageImport({ params, pict }) {
|
|
|
30106
30204
|
},
|
|
30107
30205
|
// Size
|
|
30108
30206
|
size: {
|
|
30109
|
-
width: convertToPixels(width),
|
|
30110
|
-
height: convertToPixels(height)
|
|
30207
|
+
width: convertToPixels$1(width),
|
|
30208
|
+
height: convertToPixels$1(height)
|
|
30111
30209
|
},
|
|
30112
30210
|
marginOffset: {
|
|
30113
|
-
horizontal: convertToPixels(position.marginLeft),
|
|
30114
|
-
top: convertToPixels(position.marginTop)
|
|
30211
|
+
horizontal: convertToPixels$1(position.marginLeft),
|
|
30212
|
+
top: convertToPixels$1(position.marginTop)
|
|
30115
30213
|
},
|
|
30116
30214
|
// Image adjustments
|
|
30117
30215
|
...gain && { gain },
|
|
@@ -30127,7 +30225,7 @@ function normalizeTargetPath(targetPath = "") {
|
|
|
30127
30225
|
if (trimmed.startsWith("media/")) return `word/${trimmed}`;
|
|
30128
30226
|
return `word/${trimmed}`;
|
|
30129
30227
|
}
|
|
30130
|
-
function parseVmlStyle(style) {
|
|
30228
|
+
function parseVmlStyle$1(style) {
|
|
30131
30229
|
const result = {};
|
|
30132
30230
|
if (!style) return result;
|
|
30133
30231
|
const declarations = style.split(";").filter((s) => s.trim());
|
|
@@ -30139,6 +30237,267 @@ function parseVmlStyle(style) {
|
|
|
30139
30237
|
}
|
|
30140
30238
|
return result;
|
|
30141
30239
|
}
|
|
30240
|
+
function convertToPixels$1(value) {
|
|
30241
|
+
if (typeof value === "number") return value;
|
|
30242
|
+
if (!value || typeof value !== "string") return 0;
|
|
30243
|
+
const match = value.match(/^([\d.]+)([a-z%]+)?$/i);
|
|
30244
|
+
if (!match) return 0;
|
|
30245
|
+
const num = parseFloat(match[1]);
|
|
30246
|
+
const unit = match[2] || "px";
|
|
30247
|
+
switch (unit.toLowerCase()) {
|
|
30248
|
+
case "px":
|
|
30249
|
+
return num;
|
|
30250
|
+
case "pt":
|
|
30251
|
+
return num * (96 / 72);
|
|
30252
|
+
// 1pt = 1/72 inch, 96 DPI
|
|
30253
|
+
case "in":
|
|
30254
|
+
return num * 96;
|
|
30255
|
+
case "cm":
|
|
30256
|
+
return num * (96 / 2.54);
|
|
30257
|
+
case "mm":
|
|
30258
|
+
return num * (96 / 25.4);
|
|
30259
|
+
case "pc":
|
|
30260
|
+
return num * 16;
|
|
30261
|
+
// 1pc = 12pt
|
|
30262
|
+
default:
|
|
30263
|
+
return num;
|
|
30264
|
+
}
|
|
30265
|
+
}
|
|
30266
|
+
function handleShapeTextWatermarkImport({ pict }) {
|
|
30267
|
+
const shape = pict.elements?.find((el) => el.name === "v:shape");
|
|
30268
|
+
if (!shape) return null;
|
|
30269
|
+
const textpath = shape.elements?.find((el) => el.name === "v:textpath");
|
|
30270
|
+
if (!textpath) return null;
|
|
30271
|
+
const shapeAttrs = shape.attributes || {};
|
|
30272
|
+
const textpathAttrs = textpath.attributes || {};
|
|
30273
|
+
const watermarkText = textpathAttrs["string"] || "";
|
|
30274
|
+
if (!watermarkText) {
|
|
30275
|
+
console.warn("v:textpath missing string attribute");
|
|
30276
|
+
return null;
|
|
30277
|
+
}
|
|
30278
|
+
const style = shapeAttrs.style || "";
|
|
30279
|
+
const styleObj = parseVmlStyle(style);
|
|
30280
|
+
const width = styleObj.width || "481.8pt";
|
|
30281
|
+
const height = styleObj.height || "82.8pt";
|
|
30282
|
+
const position = {
|
|
30283
|
+
type: styleObj.position || "absolute",
|
|
30284
|
+
marginLeft: styleObj["margin-left"] || "0",
|
|
30285
|
+
marginTop: styleObj["margin-top"] || "0"
|
|
30286
|
+
};
|
|
30287
|
+
const rotation = parseFloat(styleObj.rotation) || 0;
|
|
30288
|
+
const hPosition = styleObj["mso-position-horizontal"] || "center";
|
|
30289
|
+
const vPosition = styleObj["mso-position-vertical"] || "center";
|
|
30290
|
+
const hRelativeTo = styleObj["mso-position-horizontal-relative"] || "margin";
|
|
30291
|
+
const vRelativeTo = styleObj["mso-position-vertical-relative"] || "margin";
|
|
30292
|
+
const textAnchor = styleObj["v-text-anchor"] || "middle";
|
|
30293
|
+
const fill = shape.elements?.find((el) => el.name === "v:fill");
|
|
30294
|
+
const fillAttrs = fill?.attributes || {};
|
|
30295
|
+
const rawFillColor = shapeAttrs.fillcolor || fillAttrs.color || "silver";
|
|
30296
|
+
const rawFillColor2 = fillAttrs.color2 || "#3f3f3f";
|
|
30297
|
+
const fillColor = sanitizeColor(rawFillColor, "silver");
|
|
30298
|
+
const fillColor2 = sanitizeColor(rawFillColor2, "#3f3f3f");
|
|
30299
|
+
const opacity = fillAttrs.opacity || "0.5";
|
|
30300
|
+
const fillType = fillAttrs.type || "solid";
|
|
30301
|
+
const stroke = shape.elements?.find((el) => el.name === "v:stroke");
|
|
30302
|
+
const strokeAttrs = stroke?.attributes || {};
|
|
30303
|
+
const stroked = shapeAttrs.stroked || "f";
|
|
30304
|
+
const strokeColor = strokeAttrs.color || "#3465a4";
|
|
30305
|
+
const strokeJoinstyle = strokeAttrs.joinstyle || "round";
|
|
30306
|
+
const strokeEndcap = strokeAttrs.endcap || "flat";
|
|
30307
|
+
const textpathStyle = textpathAttrs.style || "";
|
|
30308
|
+
const textStyleObj = parseVmlStyle(textpathStyle);
|
|
30309
|
+
const rawFontFamily = textStyleObj["font-family"]?.replace(/['"]/g, "");
|
|
30310
|
+
const fontFamily = sanitizeFontFamily(rawFontFamily);
|
|
30311
|
+
const fontSize = textStyleObj["font-size"] || "1pt";
|
|
30312
|
+
const fitshape = textpathAttrs.fitshape || "t";
|
|
30313
|
+
const trim = textpathAttrs.trim || "t";
|
|
30314
|
+
const textpathOn = textpathAttrs.on || "t";
|
|
30315
|
+
const path = shape.elements?.find((el) => el.name === "v:path");
|
|
30316
|
+
const pathAttrs = path?.attributes || {};
|
|
30317
|
+
const textpathok = pathAttrs.textpathok || "t";
|
|
30318
|
+
const wrap2 = shape.elements?.find((el) => el.name === "w10:wrap");
|
|
30319
|
+
const wrapAttrs = wrap2?.attributes || {};
|
|
30320
|
+
const wrapType = wrapAttrs.type || "none";
|
|
30321
|
+
const widthPx = convertToPixels(width);
|
|
30322
|
+
const heightPx = convertToPixels(height);
|
|
30323
|
+
const sanitizedOpacity = sanitizeNumeric(parseFloat(opacity), 0.5, 0, 1);
|
|
30324
|
+
const sanitizedRotation = sanitizeNumeric(rotation, 0, -360, 360);
|
|
30325
|
+
const svgResult = generateTextWatermarkSVG({
|
|
30326
|
+
text: watermarkText,
|
|
30327
|
+
width: widthPx,
|
|
30328
|
+
height: heightPx,
|
|
30329
|
+
rotation: sanitizedRotation,
|
|
30330
|
+
fill: {
|
|
30331
|
+
color: fillColor,
|
|
30332
|
+
opacity: sanitizedOpacity
|
|
30333
|
+
},
|
|
30334
|
+
textStyle: {
|
|
30335
|
+
fontFamily,
|
|
30336
|
+
fontSize
|
|
30337
|
+
}
|
|
30338
|
+
});
|
|
30339
|
+
const svgDataUri = svgResult.dataUri;
|
|
30340
|
+
const imageWatermarkNode = {
|
|
30341
|
+
type: "image",
|
|
30342
|
+
attrs: {
|
|
30343
|
+
src: svgDataUri,
|
|
30344
|
+
alt: watermarkText,
|
|
30345
|
+
title: watermarkText,
|
|
30346
|
+
extension: "svg",
|
|
30347
|
+
// Mark this as a text watermark for export
|
|
30348
|
+
vmlWatermark: true,
|
|
30349
|
+
vmlTextWatermark: true,
|
|
30350
|
+
// Store VML-specific attributes for round-trip
|
|
30351
|
+
vmlStyle: style,
|
|
30352
|
+
vmlAttributes: shapeAttrs,
|
|
30353
|
+
vmlTextpathAttributes: textpathAttrs,
|
|
30354
|
+
vmlPathAttributes: pathAttrs,
|
|
30355
|
+
vmlFillAttributes: fillAttrs,
|
|
30356
|
+
vmlStrokeAttributes: strokeAttrs,
|
|
30357
|
+
vmlWrapAttributes: wrapAttrs,
|
|
30358
|
+
// Positioning (same as image watermarks)
|
|
30359
|
+
isAnchor: true,
|
|
30360
|
+
inline: false,
|
|
30361
|
+
wrap: {
|
|
30362
|
+
type: wrapType === "none" ? "None" : wrapType,
|
|
30363
|
+
attrs: {
|
|
30364
|
+
behindDoc: true
|
|
30365
|
+
}
|
|
30366
|
+
},
|
|
30367
|
+
anchorData: {
|
|
30368
|
+
hRelativeFrom: hRelativeTo,
|
|
30369
|
+
vRelativeFrom: vRelativeTo,
|
|
30370
|
+
alignH: hPosition,
|
|
30371
|
+
alignV: vPosition
|
|
30372
|
+
},
|
|
30373
|
+
// Size - use rotated bounding box dimensions to prevent clipping
|
|
30374
|
+
size: {
|
|
30375
|
+
width: svgResult.svgWidth,
|
|
30376
|
+
height: svgResult.svgHeight
|
|
30377
|
+
},
|
|
30378
|
+
marginOffset: {
|
|
30379
|
+
horizontal: convertToPixels(position.marginLeft),
|
|
30380
|
+
// For center-aligned watermarks relative to margin, Word's margin-top value
|
|
30381
|
+
// is not suitable for browser rendering. Set to 0 to let center alignment work.
|
|
30382
|
+
top: vPosition === "center" && vRelativeTo === "margin" ? 0 : convertToPixels(position.marginTop)
|
|
30383
|
+
},
|
|
30384
|
+
// Store text watermark specific data for export
|
|
30385
|
+
textWatermarkData: {
|
|
30386
|
+
text: watermarkText,
|
|
30387
|
+
rotation: sanitizedRotation,
|
|
30388
|
+
textStyle: {
|
|
30389
|
+
fontFamily,
|
|
30390
|
+
fontSize,
|
|
30391
|
+
textAnchor
|
|
30392
|
+
},
|
|
30393
|
+
fill: {
|
|
30394
|
+
color: fillColor,
|
|
30395
|
+
color2: fillColor2,
|
|
30396
|
+
opacity: sanitizedOpacity,
|
|
30397
|
+
type: fillType
|
|
30398
|
+
},
|
|
30399
|
+
stroke: {
|
|
30400
|
+
enabled: stroked !== "f",
|
|
30401
|
+
color: strokeColor,
|
|
30402
|
+
joinstyle: strokeJoinstyle,
|
|
30403
|
+
endcap: strokeEndcap
|
|
30404
|
+
},
|
|
30405
|
+
textpath: {
|
|
30406
|
+
on: textpathOn === "t",
|
|
30407
|
+
fitshape: fitshape === "t",
|
|
30408
|
+
trim: trim === "t",
|
|
30409
|
+
textpathok: textpathok === "t"
|
|
30410
|
+
}
|
|
30411
|
+
}
|
|
30412
|
+
}
|
|
30413
|
+
};
|
|
30414
|
+
return imageWatermarkNode;
|
|
30415
|
+
}
|
|
30416
|
+
function sanitizeFontFamily(fontFamily) {
|
|
30417
|
+
if (!fontFamily || typeof fontFamily !== "string") {
|
|
30418
|
+
return "Arial";
|
|
30419
|
+
}
|
|
30420
|
+
const sanitized = fontFamily.replace(/[^a-zA-Z0-9\s,\-]/g, "").trim();
|
|
30421
|
+
return sanitized || "Arial";
|
|
30422
|
+
}
|
|
30423
|
+
function sanitizeColor(color, defaultColor = "silver") {
|
|
30424
|
+
if (!color || typeof color !== "string") {
|
|
30425
|
+
return defaultColor;
|
|
30426
|
+
}
|
|
30427
|
+
const sanitized = color.replace(/[^a-zA-Z0-9#%(),.]/g, "").trim();
|
|
30428
|
+
return sanitized || defaultColor;
|
|
30429
|
+
}
|
|
30430
|
+
function sanitizeNumeric(value, defaultValue, min = -Infinity, max = Infinity) {
|
|
30431
|
+
const num = typeof value === "number" ? value : parseFloat(value);
|
|
30432
|
+
if (isNaN(num) || !isFinite(num)) {
|
|
30433
|
+
return defaultValue;
|
|
30434
|
+
}
|
|
30435
|
+
return Math.max(min, Math.min(max, num));
|
|
30436
|
+
}
|
|
30437
|
+
function generateTextWatermarkSVG({ text, width, height, rotation, fill, textStyle }) {
|
|
30438
|
+
let fontSize = height * 0.9;
|
|
30439
|
+
if (textStyle?.fontSize && textStyle.fontSize.trim() !== "1pt") {
|
|
30440
|
+
const match = textStyle.fontSize.match(/^([\d.]+)(pt|px)?$/);
|
|
30441
|
+
if (match) {
|
|
30442
|
+
const value = parseFloat(match[1]);
|
|
30443
|
+
const unit = match[2] || "pt";
|
|
30444
|
+
fontSize = (unit === "pt" ? value * (96 / 72) : value) * 50;
|
|
30445
|
+
}
|
|
30446
|
+
}
|
|
30447
|
+
fontSize = Math.max(fontSize, 48);
|
|
30448
|
+
const color = sanitizeColor(fill?.color, "silver");
|
|
30449
|
+
const opacity = sanitizeNumeric(fill?.opacity, 0.5, 0, 1);
|
|
30450
|
+
const fontFamily = sanitizeFontFamily(textStyle?.fontFamily);
|
|
30451
|
+
const sanitizedRotation = sanitizeNumeric(rotation, 0, -360, 360);
|
|
30452
|
+
const sanitizedWidth = sanitizeNumeric(width, 100, 1, 1e4);
|
|
30453
|
+
const sanitizedHeight = sanitizeNumeric(height, 100, 1, 1e4);
|
|
30454
|
+
const sanitizedFontSize = sanitizeNumeric(fontSize, 48, 1, 1e3);
|
|
30455
|
+
const radians = sanitizedRotation * Math.PI / 180;
|
|
30456
|
+
const cos = Math.abs(Math.cos(radians));
|
|
30457
|
+
const sin = Math.abs(Math.sin(radians));
|
|
30458
|
+
const rotatedWidth = sanitizedWidth * cos + sanitizedHeight * sin;
|
|
30459
|
+
const rotatedHeight = sanitizedWidth * sin + sanitizedHeight * cos;
|
|
30460
|
+
const svgWidth = Math.max(sanitizedWidth, rotatedWidth);
|
|
30461
|
+
const svgHeight = Math.max(sanitizedHeight, rotatedHeight);
|
|
30462
|
+
const centerX = svgWidth / 2;
|
|
30463
|
+
const centerY = svgHeight / 2;
|
|
30464
|
+
const svg = `<svg xmlns="http://www.w3.org/2000/svg" width="${svgWidth}" height="${svgHeight}" viewBox="0 0 ${svgWidth} ${svgHeight}">
|
|
30465
|
+
<text
|
|
30466
|
+
x="${centerX}"
|
|
30467
|
+
y="${centerY}"
|
|
30468
|
+
text-anchor="middle"
|
|
30469
|
+
dominant-baseline="middle"
|
|
30470
|
+
font-family="${fontFamily}"
|
|
30471
|
+
font-size="${sanitizedFontSize}px"
|
|
30472
|
+
font-weight="bold"
|
|
30473
|
+
fill="${color}"
|
|
30474
|
+
opacity="${opacity}"
|
|
30475
|
+
transform="rotate(${sanitizedRotation} ${centerX} ${centerY})">${escapeXml(text)}</text>
|
|
30476
|
+
</svg>`;
|
|
30477
|
+
return {
|
|
30478
|
+
dataUri: `data:image/svg+xml,${encodeURIComponent(svg)}`,
|
|
30479
|
+
svgWidth,
|
|
30480
|
+
svgHeight
|
|
30481
|
+
};
|
|
30482
|
+
}
|
|
30483
|
+
function escapeXml(text) {
|
|
30484
|
+
return text.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">").replace(/"/g, """).replace(/'/g, "'");
|
|
30485
|
+
}
|
|
30486
|
+
function parseVmlStyle(style) {
|
|
30487
|
+
const result = {};
|
|
30488
|
+
if (!style) return result;
|
|
30489
|
+
const declarations = style.split(";").filter((s) => s.trim());
|
|
30490
|
+
for (const decl of declarations) {
|
|
30491
|
+
const colonIndex = decl.indexOf(":");
|
|
30492
|
+
if (colonIndex === -1) continue;
|
|
30493
|
+
const prop = decl.substring(0, colonIndex).trim();
|
|
30494
|
+
const value = decl.substring(colonIndex + 1).trim();
|
|
30495
|
+
if (prop && value) {
|
|
30496
|
+
result[prop] = value;
|
|
30497
|
+
}
|
|
30498
|
+
}
|
|
30499
|
+
return result;
|
|
30500
|
+
}
|
|
30142
30501
|
function convertToPixels(value) {
|
|
30143
30502
|
if (typeof value === "number") return value;
|
|
30144
30503
|
if (!value || typeof value !== "string") return 0;
|
|
@@ -30183,9 +30542,13 @@ function pictNodeTypeStrategy(node) {
|
|
|
30183
30542
|
if (textbox) {
|
|
30184
30543
|
return { type: "shapeContainer", handler: handleShapeTextboxImport };
|
|
30185
30544
|
}
|
|
30545
|
+
const textpath = shape.elements?.find((el) => el.name === "v:textpath");
|
|
30546
|
+
if (textpath) {
|
|
30547
|
+
return { type: "image", handler: handleShapeTextWatermarkImport };
|
|
30548
|
+
}
|
|
30186
30549
|
const imagedata = shape.elements?.find((el) => el.name === "v:imagedata");
|
|
30187
30550
|
if (imagedata) {
|
|
30188
|
-
return { type: "image", handler:
|
|
30551
|
+
return { type: "image", handler: handleShapeImageWatermarkImport };
|
|
30189
30552
|
}
|
|
30190
30553
|
}
|
|
30191
30554
|
return { type: "unknown", handler: null };
|
|
@@ -30285,7 +30648,7 @@ function translateVRectContentBlock(params) {
|
|
|
30285
30648
|
};
|
|
30286
30649
|
return wrapTextInRun(pict);
|
|
30287
30650
|
}
|
|
30288
|
-
function
|
|
30651
|
+
function translateImageWatermark(params) {
|
|
30289
30652
|
const { node } = params;
|
|
30290
30653
|
const { attrs } = node;
|
|
30291
30654
|
if (attrs.vmlAttributes && attrs.vmlImagedata) {
|
|
@@ -30315,7 +30678,7 @@ function translateVmlWatermark(params) {
|
|
|
30315
30678
|
};
|
|
30316
30679
|
return par2;
|
|
30317
30680
|
}
|
|
30318
|
-
const style = buildVmlStyle(attrs);
|
|
30681
|
+
const style = buildVmlStyle$1(attrs);
|
|
30319
30682
|
const shape = {
|
|
30320
30683
|
name: "v:shape",
|
|
30321
30684
|
attributes: {
|
|
@@ -30350,23 +30713,23 @@ function translateVmlWatermark(params) {
|
|
|
30350
30713
|
};
|
|
30351
30714
|
return par;
|
|
30352
30715
|
}
|
|
30353
|
-
function buildVmlStyle(attrs) {
|
|
30716
|
+
function buildVmlStyle$1(attrs) {
|
|
30354
30717
|
const styles = [];
|
|
30355
30718
|
styles.push("position:absolute");
|
|
30356
30719
|
if (attrs.size) {
|
|
30357
30720
|
if (attrs.size.width) {
|
|
30358
|
-
styles.push(`width:${convertToPt(attrs.size.width)}pt`);
|
|
30721
|
+
styles.push(`width:${convertToPt$1(attrs.size.width)}pt`);
|
|
30359
30722
|
}
|
|
30360
30723
|
if (attrs.size.height) {
|
|
30361
|
-
styles.push(`height:${convertToPt(attrs.size.height)}pt`);
|
|
30724
|
+
styles.push(`height:${convertToPt$1(attrs.size.height)}pt`);
|
|
30362
30725
|
}
|
|
30363
30726
|
}
|
|
30364
30727
|
if (attrs.marginOffset) {
|
|
30365
30728
|
if (attrs.marginOffset.horizontal !== void 0) {
|
|
30366
|
-
styles.push(`margin-left:${convertToPt(attrs.marginOffset.horizontal)}pt`);
|
|
30729
|
+
styles.push(`margin-left:${convertToPt$1(attrs.marginOffset.horizontal)}pt`);
|
|
30367
30730
|
}
|
|
30368
30731
|
if (attrs.marginOffset.top !== void 0) {
|
|
30369
|
-
styles.push(`margin-top:${convertToPt(attrs.marginOffset.top)}pt`);
|
|
30732
|
+
styles.push(`margin-top:${convertToPt$1(attrs.marginOffset.top)}pt`);
|
|
30370
30733
|
}
|
|
30371
30734
|
}
|
|
30372
30735
|
if (attrs.wrap?.attrs?.behindDoc) {
|
|
@@ -30390,9 +30753,215 @@ function buildVmlStyle(attrs) {
|
|
|
30390
30753
|
styles.push("mso-height-percent:0");
|
|
30391
30754
|
return styles.join(";");
|
|
30392
30755
|
}
|
|
30393
|
-
function convertToPt(pixels) {
|
|
30756
|
+
function convertToPt$1(pixels) {
|
|
30394
30757
|
return pixels * 72 / 96;
|
|
30395
30758
|
}
|
|
30759
|
+
function translateTextWatermark(params) {
|
|
30760
|
+
const { node } = params;
|
|
30761
|
+
const { attrs } = node;
|
|
30762
|
+
const text = attrs.textWatermarkData?.text || attrs.vmlTextpathAttributes?.string || "";
|
|
30763
|
+
if (attrs.vmlAttributes && attrs.vmlTextpathAttributes) {
|
|
30764
|
+
const shapeElements2 = [];
|
|
30765
|
+
if (attrs.vmlPathAttributes) {
|
|
30766
|
+
shapeElements2.push({
|
|
30767
|
+
name: "v:path",
|
|
30768
|
+
attributes: attrs.vmlPathAttributes
|
|
30769
|
+
});
|
|
30770
|
+
}
|
|
30771
|
+
shapeElements2.push({
|
|
30772
|
+
name: "v:textpath",
|
|
30773
|
+
attributes: {
|
|
30774
|
+
...attrs.vmlTextpathAttributes,
|
|
30775
|
+
string: text
|
|
30776
|
+
}
|
|
30777
|
+
});
|
|
30778
|
+
if (attrs.vmlFillAttributes && Object.keys(attrs.vmlFillAttributes).length > 0) {
|
|
30779
|
+
shapeElements2.push({
|
|
30780
|
+
name: "v:fill",
|
|
30781
|
+
attributes: attrs.vmlFillAttributes
|
|
30782
|
+
});
|
|
30783
|
+
}
|
|
30784
|
+
if (attrs.vmlStrokeAttributes && Object.keys(attrs.vmlStrokeAttributes).length > 0) {
|
|
30785
|
+
shapeElements2.push({
|
|
30786
|
+
name: "v:stroke",
|
|
30787
|
+
attributes: attrs.vmlStrokeAttributes
|
|
30788
|
+
});
|
|
30789
|
+
}
|
|
30790
|
+
if (attrs.vmlWrapAttributes) {
|
|
30791
|
+
shapeElements2.push({
|
|
30792
|
+
name: "w10:wrap",
|
|
30793
|
+
attributes: attrs.vmlWrapAttributes
|
|
30794
|
+
});
|
|
30795
|
+
}
|
|
30796
|
+
const shape2 = {
|
|
30797
|
+
name: "v:shape",
|
|
30798
|
+
attributes: attrs.vmlAttributes,
|
|
30799
|
+
elements: shapeElements2
|
|
30800
|
+
};
|
|
30801
|
+
const pict2 = {
|
|
30802
|
+
name: "w:pict",
|
|
30803
|
+
elements: [shape2]
|
|
30804
|
+
};
|
|
30805
|
+
const par2 = {
|
|
30806
|
+
name: "w:p",
|
|
30807
|
+
elements: [wrapTextInRun(pict2)]
|
|
30808
|
+
};
|
|
30809
|
+
return par2;
|
|
30810
|
+
}
|
|
30811
|
+
const wmData = attrs.textWatermarkData || {};
|
|
30812
|
+
const style = buildVmlStyle(attrs, wmData);
|
|
30813
|
+
const textpathStyle = buildTextpathStyle(wmData);
|
|
30814
|
+
const shapeElements = [];
|
|
30815
|
+
shapeElements.push({
|
|
30816
|
+
name: "v:path",
|
|
30817
|
+
attributes: {
|
|
30818
|
+
textpathok: "t"
|
|
30819
|
+
}
|
|
30820
|
+
});
|
|
30821
|
+
shapeElements.push({
|
|
30822
|
+
name: "v:textpath",
|
|
30823
|
+
attributes: {
|
|
30824
|
+
on: "t",
|
|
30825
|
+
fitshape: "t",
|
|
30826
|
+
string: text,
|
|
30827
|
+
style: textpathStyle,
|
|
30828
|
+
...wmData.textpath?.trim !== void 0 && { trim: wmData.textpath.trim ? "t" : "f" }
|
|
30829
|
+
}
|
|
30830
|
+
});
|
|
30831
|
+
const fillAttrs = {};
|
|
30832
|
+
const fill = wmData.fill || attrs.fill;
|
|
30833
|
+
if (fill) {
|
|
30834
|
+
if (fill.type) fillAttrs.type = fill.type;
|
|
30835
|
+
if (fill.color2) fillAttrs.color2 = fill.color2;
|
|
30836
|
+
if (fill.opacity !== void 0) fillAttrs.opacity = fill.opacity.toString();
|
|
30837
|
+
if (fill.detectmouseclick !== void 0) {
|
|
30838
|
+
fillAttrs["o:detectmouseclick"] = fill.detectmouseclick ? "t" : "f";
|
|
30839
|
+
}
|
|
30840
|
+
}
|
|
30841
|
+
if (Object.keys(fillAttrs).length > 0) {
|
|
30842
|
+
shapeElements.push({
|
|
30843
|
+
name: "v:fill",
|
|
30844
|
+
attributes: fillAttrs
|
|
30845
|
+
});
|
|
30846
|
+
}
|
|
30847
|
+
const stroke = wmData.stroke || attrs.stroke;
|
|
30848
|
+
if (stroke && stroke.enabled !== false) {
|
|
30849
|
+
const strokeAttrs = {};
|
|
30850
|
+
if (stroke.color) strokeAttrs.color = stroke.color;
|
|
30851
|
+
if (stroke.joinstyle) strokeAttrs.joinstyle = stroke.joinstyle;
|
|
30852
|
+
if (stroke.endcap) strokeAttrs.endcap = stroke.endcap;
|
|
30853
|
+
if (Object.keys(strokeAttrs).length > 0) {
|
|
30854
|
+
shapeElements.push({
|
|
30855
|
+
name: "v:stroke",
|
|
30856
|
+
attributes: strokeAttrs
|
|
30857
|
+
});
|
|
30858
|
+
}
|
|
30859
|
+
}
|
|
30860
|
+
shapeElements.push({
|
|
30861
|
+
name: "w10:wrap",
|
|
30862
|
+
attributes: {
|
|
30863
|
+
type: attrs.wrap?.type?.toLowerCase() || "none"
|
|
30864
|
+
}
|
|
30865
|
+
});
|
|
30866
|
+
const shape = {
|
|
30867
|
+
name: "v:shape",
|
|
30868
|
+
attributes: {
|
|
30869
|
+
id: `PowerPlusWaterMarkObject${generateRandomSigned32BitIntStrId().replace("-", "")}`,
|
|
30870
|
+
"o:spid": `shape_${Math.floor(Math.random() * 1e4)}`,
|
|
30871
|
+
type: "#_x0000_t136",
|
|
30872
|
+
style,
|
|
30873
|
+
fillcolor: fill?.color || "silver",
|
|
30874
|
+
stroked: stroke?.enabled !== false ? "t" : "f",
|
|
30875
|
+
"o:allowincell": "f",
|
|
30876
|
+
...attrs.vmlAttributes?.adj && { adj: attrs.vmlAttributes.adj }
|
|
30877
|
+
},
|
|
30878
|
+
elements: shapeElements
|
|
30879
|
+
};
|
|
30880
|
+
const pict = {
|
|
30881
|
+
name: "w:pict",
|
|
30882
|
+
elements: [shape]
|
|
30883
|
+
};
|
|
30884
|
+
const par = {
|
|
30885
|
+
name: "w:p",
|
|
30886
|
+
elements: [wrapTextInRun(pict)]
|
|
30887
|
+
};
|
|
30888
|
+
return par;
|
|
30889
|
+
}
|
|
30890
|
+
function buildVmlStyle(attrs, wmData) {
|
|
30891
|
+
const styles = [];
|
|
30892
|
+
styles.push("position:absolute");
|
|
30893
|
+
if (attrs.marginOffset) {
|
|
30894
|
+
if (attrs.marginOffset.horizontal !== void 0) {
|
|
30895
|
+
styles.push(`margin-left:${convertToPt(attrs.marginOffset.horizontal)}pt`);
|
|
30896
|
+
}
|
|
30897
|
+
if (attrs.marginOffset.top !== void 0) {
|
|
30898
|
+
styles.push(`margin-top:${convertToPt(attrs.marginOffset.top)}pt`);
|
|
30899
|
+
}
|
|
30900
|
+
} else {
|
|
30901
|
+
styles.push("margin-left:0.05pt");
|
|
30902
|
+
styles.push("margin-top:315.7pt");
|
|
30903
|
+
}
|
|
30904
|
+
if (attrs.size) {
|
|
30905
|
+
if (attrs.size.width) {
|
|
30906
|
+
styles.push(`width:${convertToPt(attrs.size.width)}pt`);
|
|
30907
|
+
}
|
|
30908
|
+
if (attrs.size.height) {
|
|
30909
|
+
styles.push(`height:${convertToPt(attrs.size.height)}pt`);
|
|
30910
|
+
}
|
|
30911
|
+
}
|
|
30912
|
+
const wrapType = attrs.wrap?.type;
|
|
30913
|
+
let msoWrapStyle = "none";
|
|
30914
|
+
if (wrapType) {
|
|
30915
|
+
const wrapTypeLower = wrapType.toLowerCase();
|
|
30916
|
+
if (wrapTypeLower === "topandbottom") {
|
|
30917
|
+
msoWrapStyle = "top-and-bottom";
|
|
30918
|
+
} else if (["square", "tight", "through"].includes(wrapTypeLower)) {
|
|
30919
|
+
msoWrapStyle = wrapTypeLower;
|
|
30920
|
+
}
|
|
30921
|
+
}
|
|
30922
|
+
styles.push(`mso-wrap-style:${msoWrapStyle}`);
|
|
30923
|
+
const textAnchor = wmData.textStyle?.textAnchor || attrs.textStyle?.textAnchor;
|
|
30924
|
+
if (textAnchor) {
|
|
30925
|
+
styles.push(`v-text-anchor:${textAnchor}`);
|
|
30926
|
+
}
|
|
30927
|
+
const rotation = wmData.rotation || attrs.rotation;
|
|
30928
|
+
if (rotation !== void 0 && rotation !== 0) {
|
|
30929
|
+
styles.push(`rotation:${rotation}`);
|
|
30930
|
+
}
|
|
30931
|
+
if (attrs.anchorData) {
|
|
30932
|
+
if (attrs.anchorData.alignH) {
|
|
30933
|
+
styles.push(`mso-position-horizontal:${attrs.anchorData.alignH}`);
|
|
30934
|
+
}
|
|
30935
|
+
if (attrs.anchorData.alignV) {
|
|
30936
|
+
styles.push(`mso-position-vertical:${attrs.anchorData.alignV}`);
|
|
30937
|
+
}
|
|
30938
|
+
if (attrs.anchorData.hRelativeFrom) {
|
|
30939
|
+
styles.push(`mso-position-horizontal-relative:${attrs.anchorData.hRelativeFrom}`);
|
|
30940
|
+
}
|
|
30941
|
+
if (attrs.anchorData.vRelativeFrom) {
|
|
30942
|
+
styles.push(`mso-position-vertical-relative:${attrs.anchorData.vRelativeFrom}`);
|
|
30943
|
+
}
|
|
30944
|
+
}
|
|
30945
|
+
return styles.join(";");
|
|
30946
|
+
}
|
|
30947
|
+
function buildTextpathStyle(wmData) {
|
|
30948
|
+
const styles = [];
|
|
30949
|
+
if (wmData.textStyle) {
|
|
30950
|
+
if (wmData.textStyle.fontFamily) {
|
|
30951
|
+
styles.push(`font-family:"${wmData.textStyle.fontFamily}"`);
|
|
30952
|
+
}
|
|
30953
|
+
if (wmData.textStyle.fontSize) {
|
|
30954
|
+
styles.push(`font-size:${wmData.textStyle.fontSize}`);
|
|
30955
|
+
}
|
|
30956
|
+
}
|
|
30957
|
+
return styles.join(";");
|
|
30958
|
+
}
|
|
30959
|
+
function convertToPt(pixels) {
|
|
30960
|
+
if (typeof pixels === "number") {
|
|
30961
|
+
return pixels * 72 / 96;
|
|
30962
|
+
}
|
|
30963
|
+
return parseFloat(pixels) || 0;
|
|
30964
|
+
}
|
|
30396
30965
|
const XML_NODE_NAME = "w:pict";
|
|
30397
30966
|
const SD_NODE_NAME = ["shapeContainer", "contentBlock", "image"];
|
|
30398
30967
|
const validXmlAttributes = [];
|
|
@@ -30420,7 +30989,10 @@ function decode(params) {
|
|
|
30420
30989
|
contentBlock: () => translateContentBlock(params),
|
|
30421
30990
|
image: () => {
|
|
30422
30991
|
if (node.attrs?.vmlWatermark) {
|
|
30423
|
-
|
|
30992
|
+
if (node.attrs?.vmlTextWatermark) {
|
|
30993
|
+
return translateTextWatermark(params);
|
|
30994
|
+
}
|
|
30995
|
+
return translateImageWatermark(params);
|
|
30424
30996
|
}
|
|
30425
30997
|
return null;
|
|
30426
30998
|
},
|
|
@@ -31565,7 +32137,7 @@ class SuperConverter {
|
|
|
31565
32137
|
static getStoredSuperdocVersion(docx) {
|
|
31566
32138
|
return SuperConverter.getStoredCustomProperty(docx, "SuperdocVersion");
|
|
31567
32139
|
}
|
|
31568
|
-
static setStoredSuperdocVersion(docx = this.convertedXml, version = "1.5.0-next.
|
|
32140
|
+
static setStoredSuperdocVersion(docx = this.convertedXml, version = "1.5.0-next.7") {
|
|
31569
32141
|
return SuperConverter.setStoredCustomProperty(docx, "SuperdocVersion", version, false);
|
|
31570
32142
|
}
|
|
31571
32143
|
/**
|
|
@@ -32274,8 +32846,8 @@ exports.registeredHandlers = registeredHandlers;
|
|
|
32274
32846
|
exports.replaceStep = replaceStep;
|
|
32275
32847
|
exports.resolveDocxFontFamily = resolveDocxFontFamily;
|
|
32276
32848
|
exports.resolveRunProperties = resolveRunProperties;
|
|
32277
|
-
exports.translator = translator$
|
|
32278
|
-
exports.translator$1 = translator$
|
|
32849
|
+
exports.translator = translator$1O;
|
|
32850
|
+
exports.translator$1 = translator$14;
|
|
32279
32851
|
exports.unflattenListsInHtml = unflattenListsInHtml;
|
|
32280
32852
|
exports.updateNumberingProperties = updateNumberingProperties;
|
|
32281
32853
|
exports.wrapTextsInRuns = wrapTextsInRuns;
|