@pptx-studio/model 0.1.3 → 0.2.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/CHANGELOG.md +28 -0
- package/README.md +26 -1
- package/dist/index.d.ts +121 -2
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +291 -61
- package/dist/index.js.map +1 -1
- package/package.json +4 -4
package/dist/index.js
CHANGED
|
@@ -40,7 +40,8 @@ const MODEL_ERROR_CODES = [
|
|
|
40
40
|
"MODEL_TEXT_ATTR",
|
|
41
41
|
"MODEL_TEXT_FIELD",
|
|
42
42
|
"MODEL_TEXT_LEVEL",
|
|
43
|
-
"MODEL_TEXT_TYPEFACE"
|
|
43
|
+
"MODEL_TEXT_TYPEFACE",
|
|
44
|
+
"MODEL_TABLE_ATTR"
|
|
44
45
|
];
|
|
45
46
|
//#endregion
|
|
46
47
|
//#region src/types.ts
|
|
@@ -825,6 +826,65 @@ function parseGeometry(spPr, partName) {
|
|
|
825
826
|
};
|
|
826
827
|
}
|
|
827
828
|
//#endregion
|
|
829
|
+
//#region src/table.ts
|
|
830
|
+
/** `a:graphicData/@uri` of a table. */
|
|
831
|
+
const TABLE_URI = "http://schemas.openxmlformats.org/drawingml/2006/table";
|
|
832
|
+
/** The column PowerPoint invents for a grid that declares none, empty: two margins and 2 pt. */
|
|
833
|
+
const INVENTED_COLUMN_WIDTH = 208280;
|
|
834
|
+
/** A span as PowerPoint counts it: zero is one, a negative runs to the edge. */
|
|
835
|
+
function spanOf(written) {
|
|
836
|
+
return written < 0 ? Number.POSITIVE_INFINITY : Math.max(1, written);
|
|
837
|
+
}
|
|
838
|
+
/**
|
|
839
|
+
* The occupancy C7 measured, 76/76 against 52/76 for the flags: each `a:tc` takes the next
|
|
840
|
+
* column, a claimed position is covered whatever it says, a span stops at the edge or a claim.
|
|
841
|
+
*/
|
|
842
|
+
function tableGrid(table) {
|
|
843
|
+
const widths = table.columns.length === 0 ? [INVENTED_COLUMN_WIDTH] : table.columns.map((c) => c.w);
|
|
844
|
+
const heights = table.rows.length === 0 ? [0] : table.rows.map((r) => r.h);
|
|
845
|
+
const rows = heights.length;
|
|
846
|
+
const cols = widths.length;
|
|
847
|
+
const grid = Array.from({ length: rows }, () => Array.from({ length: cols }).fill(null));
|
|
848
|
+
const anchors = [];
|
|
849
|
+
const place = (anchor) => {
|
|
850
|
+
anchors.push(anchor);
|
|
851
|
+
for (let r = anchor.row; r < anchor.row + anchor.rows; r++) for (let c = anchor.col; c < anchor.col + anchor.cols; c++) grid[r][c] = anchor;
|
|
852
|
+
};
|
|
853
|
+
(table.columns.length === 0 ? [] : table.rows).forEach((row, r) => {
|
|
854
|
+
row.cells.forEach((cell, c) => {
|
|
855
|
+
if (c >= cols || grid[r][c] !== null) return;
|
|
856
|
+
const wide = spanOf(cell.gridSpan);
|
|
857
|
+
const tall = spanOf(cell.rowSpan);
|
|
858
|
+
let width = 1;
|
|
859
|
+
while (c + width < cols && width < wide && grid[r][c + width] === null) width += 1;
|
|
860
|
+
const height = Math.min(tall, rows - r);
|
|
861
|
+
place({
|
|
862
|
+
row: r,
|
|
863
|
+
col: c,
|
|
864
|
+
rows: height,
|
|
865
|
+
cols: width,
|
|
866
|
+
cell
|
|
867
|
+
});
|
|
868
|
+
});
|
|
869
|
+
});
|
|
870
|
+
for (let r = 0; r < rows; r++) for (let c = 0; c < cols; c++) if (grid[r][c] === null) place({
|
|
871
|
+
row: r,
|
|
872
|
+
col: c,
|
|
873
|
+
rows: 1,
|
|
874
|
+
cols: 1,
|
|
875
|
+
cell: null
|
|
876
|
+
});
|
|
877
|
+
anchors.sort((a, b) => a.row - b.row || a.col - b.col);
|
|
878
|
+
return {
|
|
879
|
+
rows,
|
|
880
|
+
cols,
|
|
881
|
+
widths,
|
|
882
|
+
heights,
|
|
883
|
+
positions: grid.map((line) => line.map((owner) => owner)),
|
|
884
|
+
anchors
|
|
885
|
+
};
|
|
886
|
+
}
|
|
887
|
+
//#endregion
|
|
828
888
|
//#region src/parse/body.ts
|
|
829
889
|
/**
|
|
830
890
|
* `a:bodyPr`: the text frame, as the file states it.
|
|
@@ -833,14 +893,14 @@ function parseGeometry(spPr, partName) {
|
|
|
833
893
|
* frame that states no anchor is not a top-anchored frame, and 3.6 measured that
|
|
834
894
|
* the difference is the whole of the placeholder cascade.
|
|
835
895
|
*/
|
|
836
|
-
const ANCHORS = [
|
|
896
|
+
const ANCHORS$1 = [
|
|
837
897
|
"t",
|
|
838
898
|
"ctr",
|
|
839
899
|
"b",
|
|
840
900
|
"just",
|
|
841
901
|
"dist"
|
|
842
902
|
];
|
|
843
|
-
const VERTICALS = [
|
|
903
|
+
const VERTICALS$1 = [
|
|
844
904
|
"horz",
|
|
845
905
|
"vert",
|
|
846
906
|
"vert270",
|
|
@@ -855,28 +915,28 @@ const VERT_OVERFLOWS = [
|
|
|
855
915
|
"ellipsis",
|
|
856
916
|
"clip"
|
|
857
917
|
];
|
|
858
|
-
const HORZ_OVERFLOWS = ["overflow", "clip"];
|
|
859
|
-
function attrError(element, name, raw, why, part) {
|
|
918
|
+
const HORZ_OVERFLOWS$1 = ["overflow", "clip"];
|
|
919
|
+
function attrError$1(element, name, raw, why, part) {
|
|
860
920
|
throw new ModelError("MODEL_TEXT_ATTR", `${element.qname}/@${name} is "${raw}", which is not ${why}`, part, name);
|
|
861
921
|
}
|
|
862
|
-
function boolOf$
|
|
922
|
+
function boolOf$2(element, name, part) {
|
|
863
923
|
const raw = attributeValue(element, name);
|
|
864
924
|
if (raw === void 0) return void 0;
|
|
865
925
|
if (raw === "1" || raw === "true") return true;
|
|
866
926
|
if (raw === "0" || raw === "false") return false;
|
|
867
|
-
return attrError(element, name, raw, "a ST_OnOff", part);
|
|
927
|
+
return attrError$1(element, name, raw, "a ST_OnOff", part);
|
|
868
928
|
}
|
|
869
|
-
function intOf$
|
|
929
|
+
function intOf$3(element, name, part) {
|
|
870
930
|
const raw = attributeValue(element, name);
|
|
871
931
|
if (raw === void 0) return void 0;
|
|
872
932
|
const value = Number(raw);
|
|
873
|
-
if (!Number.isInteger(value)) return attrError(element, name, raw, "an integer", part);
|
|
933
|
+
if (!Number.isInteger(value)) return attrError$1(element, name, raw, "an integer", part);
|
|
874
934
|
return value;
|
|
875
935
|
}
|
|
876
|
-
function enumOf$
|
|
936
|
+
function enumOf$2(element, name, allowed, part) {
|
|
877
937
|
const raw = attributeValue(element, name);
|
|
878
938
|
if (raw === void 0) return void 0;
|
|
879
|
-
if (!allowed.includes(raw)) return attrError(element, name, raw, `one of ${allowed.join(", ")}`, part);
|
|
939
|
+
if (!allowed.includes(raw)) return attrError$1(element, name, raw, `one of ${allowed.join(", ")}`, part);
|
|
880
940
|
return raw;
|
|
881
941
|
}
|
|
882
942
|
/**
|
|
@@ -902,31 +962,31 @@ function percentOf(element, name, part) {
|
|
|
902
962
|
const raw = attributeValue(element, name);
|
|
903
963
|
if (raw === void 0) return void 0;
|
|
904
964
|
const value = raw.endsWith("%") ? Number(raw.slice(0, -1)) * 1e3 : Number(raw);
|
|
905
|
-
if (!Number.isFinite(value)) return attrError(element, name, raw, "a ST_Percentage", part);
|
|
965
|
+
if (!Number.isFinite(value)) return attrError$1(element, name, raw, "a ST_Percentage", part);
|
|
906
966
|
return value;
|
|
907
967
|
}
|
|
908
968
|
/** Parse an `a:bodyPr`. Lengths stay in EMU and angles in 60000ths of a degree. */
|
|
909
969
|
function parseBodyProps(element, partName) {
|
|
910
970
|
return {
|
|
911
|
-
anchor: enumOf$
|
|
912
|
-
anchorCtr: boolOf$
|
|
913
|
-
lIns: intOf$
|
|
914
|
-
tIns: intOf$
|
|
915
|
-
rIns: intOf$
|
|
916
|
-
bIns: intOf$
|
|
917
|
-
vert: enumOf$
|
|
918
|
-
wrap: enumOf$
|
|
919
|
-
vertOverflow: enumOf$
|
|
920
|
-
horzOverflow: enumOf$
|
|
921
|
-
rot: intOf$
|
|
922
|
-
upright: boolOf$
|
|
923
|
-
numCol: intOf$
|
|
924
|
-
spcCol: intOf$
|
|
925
|
-
rtlCol: boolOf$
|
|
926
|
-
spcFirstLastPara: boolOf$
|
|
927
|
-
compatLnSpc: boolOf$
|
|
928
|
-
fromWordArt: boolOf$
|
|
929
|
-
forceAA: boolOf$
|
|
971
|
+
anchor: enumOf$2(element, "anchor", ANCHORS$1, partName),
|
|
972
|
+
anchorCtr: boolOf$2(element, "anchorCtr", partName),
|
|
973
|
+
lIns: intOf$3(element, "lIns", partName),
|
|
974
|
+
tIns: intOf$3(element, "tIns", partName),
|
|
975
|
+
rIns: intOf$3(element, "rIns", partName),
|
|
976
|
+
bIns: intOf$3(element, "bIns", partName),
|
|
977
|
+
vert: enumOf$2(element, "vert", VERTICALS$1, partName),
|
|
978
|
+
wrap: enumOf$2(element, "wrap", WRAPS, partName),
|
|
979
|
+
vertOverflow: enumOf$2(element, "vertOverflow", VERT_OVERFLOWS, partName),
|
|
980
|
+
horzOverflow: enumOf$2(element, "horzOverflow", HORZ_OVERFLOWS$1, partName),
|
|
981
|
+
rot: intOf$3(element, "rot", partName),
|
|
982
|
+
upright: boolOf$2(element, "upright", partName),
|
|
983
|
+
numCol: intOf$3(element, "numCol", partName),
|
|
984
|
+
spcCol: intOf$3(element, "spcCol", partName),
|
|
985
|
+
rtlCol: boolOf$2(element, "rtlCol", partName),
|
|
986
|
+
spcFirstLastPara: boolOf$2(element, "spcFirstLastPara", partName),
|
|
987
|
+
compatLnSpc: boolOf$2(element, "compatLnSpc", partName),
|
|
988
|
+
fromWordArt: boolOf$2(element, "fromWordArt", partName),
|
|
989
|
+
forceAA: boolOf$2(element, "forceAA", partName),
|
|
930
990
|
autofit: parseAutofit(element, partName),
|
|
931
991
|
node: element
|
|
932
992
|
};
|
|
@@ -975,14 +1035,14 @@ const LEVELS = 9;
|
|
|
975
1035
|
* `1`/`true` and `0`/`false`. Anything else is a file that says something we do
|
|
976
1036
|
* not understand, and guessing is how an explicit `b="0"` becomes bold.
|
|
977
1037
|
*/
|
|
978
|
-
function boolOf(element, name, partName) {
|
|
1038
|
+
function boolOf$1(element, name, partName) {
|
|
979
1039
|
const raw = attributeValue(element, name);
|
|
980
1040
|
if (raw === void 0) return void 0;
|
|
981
1041
|
if (raw === "1" || raw === "true") return true;
|
|
982
1042
|
if (raw === "0" || raw === "false") return false;
|
|
983
1043
|
throw new ModelError("MODEL_TEXT_ATTR", `${element.qname}/@${name} is "${raw}", which is not a ST_OnOff`, partName, name);
|
|
984
1044
|
}
|
|
985
|
-
function intOf$
|
|
1045
|
+
function intOf$2(element, name, partName) {
|
|
986
1046
|
const raw = attributeValue(element, name);
|
|
987
1047
|
if (raw === void 0) return void 0;
|
|
988
1048
|
const value = Number(raw);
|
|
@@ -997,7 +1057,7 @@ function intOf$1(element, name, partName) {
|
|
|
997
1057
|
* by, and `ST_TextAlignType` in particular has a member - `just` - whose
|
|
998
1058
|
* substitute would be plausible on most slides and wrong on the rest.
|
|
999
1059
|
*/
|
|
1000
|
-
function enumOf(element, name, allowed, partName) {
|
|
1060
|
+
function enumOf$1(element, name, allowed, partName) {
|
|
1001
1061
|
const raw = attributeValue(element, name);
|
|
1002
1062
|
if (raw === void 0) return void 0;
|
|
1003
1063
|
if (!allowed.includes(raw)) throw new ModelError("MODEL_TEXT_ATTR", `${element.qname}/@${name} is "${raw}", which is not one of ${allowed.join(", ")}`, partName, name);
|
|
@@ -1063,8 +1123,8 @@ function typefaceOf(element, partName) {
|
|
|
1063
1123
|
return {
|
|
1064
1124
|
typeface,
|
|
1065
1125
|
panose: attributeValue(element, "panose"),
|
|
1066
|
-
pitchFamily: intOf$
|
|
1067
|
-
charset: intOf$
|
|
1126
|
+
pitchFamily: intOf$2(element, "pitchFamily", partName),
|
|
1127
|
+
charset: intOf$2(element, "charset", partName)
|
|
1068
1128
|
};
|
|
1069
1129
|
}
|
|
1070
1130
|
/**
|
|
@@ -1082,16 +1142,16 @@ function parseTypeface(parent, qname, partName) {
|
|
|
1082
1142
|
/** `a:rPr`, `a:defRPr` or `a:endParaRPr` - one type under three names. */
|
|
1083
1143
|
function parseRunProps(element, partName) {
|
|
1084
1144
|
return {
|
|
1085
|
-
sz: intOf$
|
|
1086
|
-
b: boolOf(element, "b", partName),
|
|
1087
|
-
i: boolOf(element, "i", partName),
|
|
1088
|
-
u: enumOf(element, "u", UNDERLINE, partName),
|
|
1089
|
-
strike: enumOf(element, "strike", STRIKE, partName),
|
|
1090
|
-
cap: enumOf(element, "cap", CAPS, partName),
|
|
1091
|
-
spc: intOf$
|
|
1092
|
-
kern: intOf$
|
|
1093
|
-
baseline: intOf$
|
|
1094
|
-
noProof: boolOf(element, "noProof", partName),
|
|
1145
|
+
sz: intOf$2(element, "sz", partName),
|
|
1146
|
+
b: boolOf$1(element, "b", partName),
|
|
1147
|
+
i: boolOf$1(element, "i", partName),
|
|
1148
|
+
u: enumOf$1(element, "u", UNDERLINE, partName),
|
|
1149
|
+
strike: enumOf$1(element, "strike", STRIKE, partName),
|
|
1150
|
+
cap: enumOf$1(element, "cap", CAPS, partName),
|
|
1151
|
+
spc: intOf$2(element, "spc", partName),
|
|
1152
|
+
kern: intOf$2(element, "kern", partName),
|
|
1153
|
+
baseline: intOf$2(element, "baseline", partName),
|
|
1154
|
+
noProof: boolOf$1(element, "noProof", partName),
|
|
1095
1155
|
lang: attributeValue(element, "lang"),
|
|
1096
1156
|
altLang: attributeValue(element, "altLang"),
|
|
1097
1157
|
latin: parseTypeface(element, "a:latin", partName),
|
|
@@ -1131,7 +1191,7 @@ function parseSpacing(parent, qname, partName) {
|
|
|
1131
1191
|
}
|
|
1132
1192
|
const pts = firstChild(element, "a:spcPts");
|
|
1133
1193
|
if (pts !== void 0) {
|
|
1134
|
-
const value = intOf$
|
|
1194
|
+
const value = intOf$2(pts, "val", partName);
|
|
1135
1195
|
if (value === void 0) throw new ModelError("MODEL_TEXT_ATTR", `${qname}/a:spcPts has no @val`, partName, qname);
|
|
1136
1196
|
return {
|
|
1137
1197
|
kind: "points",
|
|
@@ -1142,16 +1202,16 @@ function parseSpacing(parent, qname, partName) {
|
|
|
1142
1202
|
/** `a:pPr`, `a:defPPr` or any `a:lvlNpPr` - one type under eleven names. */
|
|
1143
1203
|
function parseParaProps(element, partName) {
|
|
1144
1204
|
return {
|
|
1145
|
-
marL: intOf$
|
|
1146
|
-
marR: intOf$
|
|
1147
|
-
indent: intOf$
|
|
1148
|
-
algn: enumOf(element, "algn", ALIGN, partName),
|
|
1149
|
-
defTabSz: intOf$
|
|
1150
|
-
rtl: boolOf(element, "rtl", partName),
|
|
1151
|
-
eaLnBrk: boolOf(element, "eaLnBrk", partName),
|
|
1152
|
-
fontAlgn: enumOf(element, "fontAlgn", FONT_ALIGN, partName),
|
|
1153
|
-
latinLnBrk: boolOf(element, "latinLnBrk", partName),
|
|
1154
|
-
hangingPunct: boolOf(element, "hangingPunct", partName),
|
|
1205
|
+
marL: intOf$2(element, "marL", partName),
|
|
1206
|
+
marR: intOf$2(element, "marR", partName),
|
|
1207
|
+
indent: intOf$2(element, "indent", partName),
|
|
1208
|
+
algn: enumOf$1(element, "algn", ALIGN, partName),
|
|
1209
|
+
defTabSz: intOf$2(element, "defTabSz", partName),
|
|
1210
|
+
rtl: boolOf$1(element, "rtl", partName),
|
|
1211
|
+
eaLnBrk: boolOf$1(element, "eaLnBrk", partName),
|
|
1212
|
+
fontAlgn: enumOf$1(element, "fontAlgn", FONT_ALIGN, partName),
|
|
1213
|
+
latinLnBrk: boolOf$1(element, "latinLnBrk", partName),
|
|
1214
|
+
hangingPunct: boolOf$1(element, "hangingPunct", partName),
|
|
1155
1215
|
lnSpc: parseSpacing(element, "a:lnSpc", partName),
|
|
1156
1216
|
spcBef: parseSpacing(element, "a:spcBef", partName),
|
|
1157
1217
|
spcAft: parseSpacing(element, "a:spcAft", partName),
|
|
@@ -1200,7 +1260,7 @@ function parseBullet(element, partName) {
|
|
|
1200
1260
|
if (type === void 0) throw new ModelError("MODEL_TEXT_BULLET", "a:buAutoNum has no @type, which the schema requires", partName, "a:buAutoNum");
|
|
1201
1261
|
buAutoNum = {
|
|
1202
1262
|
type,
|
|
1203
|
-
startAt: intOf$
|
|
1263
|
+
startAt: intOf$2(autoNum, "startAt", partName)
|
|
1204
1264
|
};
|
|
1205
1265
|
}
|
|
1206
1266
|
let buBlip;
|
|
@@ -1253,7 +1313,7 @@ function requiredPercentage(element, partName, what) {
|
|
|
1253
1313
|
}
|
|
1254
1314
|
/** `@val` on a `a:buSzPts`, in hundredths of a point. */
|
|
1255
1315
|
function requiredInt(element, partName, what) {
|
|
1256
|
-
const value = intOf$
|
|
1316
|
+
const value = intOf$2(element, "val", partName);
|
|
1257
1317
|
if (value === void 0) throw new ModelError("MODEL_TEXT_BULLET", `${what} has no @val`, partName, what);
|
|
1258
1318
|
return value;
|
|
1259
1319
|
}
|
|
@@ -1307,7 +1367,7 @@ function parseDefaultTextStyle(presentation, partName) {
|
|
|
1307
1367
|
*/
|
|
1308
1368
|
function levelOf(pPr, partName) {
|
|
1309
1369
|
if (pPr === void 0) return 0;
|
|
1310
|
-
const lvl = intOf$
|
|
1370
|
+
const lvl = intOf$2(pPr, "lvl", partName);
|
|
1311
1371
|
if (lvl === void 0) return 0;
|
|
1312
1372
|
return Math.max(0, Math.min(8, lvl));
|
|
1313
1373
|
}
|
|
@@ -1371,6 +1431,175 @@ function parseTextBodyChild(parent, partName) {
|
|
|
1371
1431
|
return element === void 0 ? void 0 : parseTextBody(element, partName);
|
|
1372
1432
|
}
|
|
1373
1433
|
//#endregion
|
|
1434
|
+
//#region src/parse/table.ts
|
|
1435
|
+
/**
|
|
1436
|
+
* `a:tbl` into a `Table`: the grid, the rows, every cell's spans, body and properties.
|
|
1437
|
+
* Nothing here resolves the merges; `tableGrid` does, by the rule C7 measured.
|
|
1438
|
+
*/
|
|
1439
|
+
const ANCHORS = [
|
|
1440
|
+
"t",
|
|
1441
|
+
"ctr",
|
|
1442
|
+
"b",
|
|
1443
|
+
"just",
|
|
1444
|
+
"dist"
|
|
1445
|
+
];
|
|
1446
|
+
const VERTICALS = [
|
|
1447
|
+
"horz",
|
|
1448
|
+
"vert",
|
|
1449
|
+
"vert270",
|
|
1450
|
+
"wordArtVert",
|
|
1451
|
+
"eaVert",
|
|
1452
|
+
"mongolianVert",
|
|
1453
|
+
"wordArtVertRtl"
|
|
1454
|
+
];
|
|
1455
|
+
const HORZ_OVERFLOWS = ["overflow", "clip"];
|
|
1456
|
+
/** EMU per unit of `ST_UniversalMeasure`. */
|
|
1457
|
+
const UNITS = {
|
|
1458
|
+
mm: 36e3,
|
|
1459
|
+
cm: 36e4,
|
|
1460
|
+
in: 914400,
|
|
1461
|
+
pt: 12700,
|
|
1462
|
+
pc: 152400,
|
|
1463
|
+
pi: 152400
|
|
1464
|
+
};
|
|
1465
|
+
function attrError(element, name, raw, why, part) {
|
|
1466
|
+
throw new ModelError("MODEL_TABLE_ATTR", `${element.qname}/@${name} is "${raw}", which is not ${why}`, part, name);
|
|
1467
|
+
}
|
|
1468
|
+
function boolOf(element, name, part) {
|
|
1469
|
+
const raw = attributeValue(element, name);
|
|
1470
|
+
if (raw === void 0) return void 0;
|
|
1471
|
+
if (raw === "1" || raw === "true") return true;
|
|
1472
|
+
if (raw === "0" || raw === "false") return false;
|
|
1473
|
+
return attrError(element, name, raw, "an xsd:boolean", part);
|
|
1474
|
+
}
|
|
1475
|
+
function intOf$1(element, name, part) {
|
|
1476
|
+
const raw = attributeValue(element, name);
|
|
1477
|
+
if (raw === void 0) return void 0;
|
|
1478
|
+
if (!/^[+-]?\d+$/.test(raw)) return attrError(element, name, raw, "an xsd:int", part);
|
|
1479
|
+
return Number(raw);
|
|
1480
|
+
}
|
|
1481
|
+
/** `ST_Coordinate`: EMU, or a universal measure such as `108pt`, which PowerPoint honours. */
|
|
1482
|
+
function coordinateOf(element, name, part) {
|
|
1483
|
+
const raw = attributeValue(element, name);
|
|
1484
|
+
if (raw === void 0) return void 0;
|
|
1485
|
+
if (/^[+-]?\d+$/.test(raw)) return Number(raw);
|
|
1486
|
+
const measure = /^(-?\d+(?:\.\d+)?)(mm|cm|in|pt|pc|pi)$/.exec(raw);
|
|
1487
|
+
if (measure === null) return attrError(element, name, raw, "a ST_Coordinate", part);
|
|
1488
|
+
return Math.round(Number(measure[1]) * UNITS[measure[2]]);
|
|
1489
|
+
}
|
|
1490
|
+
function required(element, name, value, part) {
|
|
1491
|
+
if (value === void 0) throw new ModelError("MODEL_TABLE_ATTR", `${element.qname} has no @${name}, which the schema requires`, part, name);
|
|
1492
|
+
return value;
|
|
1493
|
+
}
|
|
1494
|
+
function enumOf(element, name, allowed, part) {
|
|
1495
|
+
const raw = attributeValue(element, name);
|
|
1496
|
+
if (raw === void 0) return void 0;
|
|
1497
|
+
if (!allowed.includes(raw)) return attrError(element, name, raw, `one of ${allowed.join(", ")}`, part);
|
|
1498
|
+
return raw;
|
|
1499
|
+
}
|
|
1500
|
+
function lineChild(parent, qname, part) {
|
|
1501
|
+
const element = firstChild(parent, qname);
|
|
1502
|
+
return element === void 0 ? void 0 : parseLineElement(element, part);
|
|
1503
|
+
}
|
|
1504
|
+
function parseCellProps(element, part) {
|
|
1505
|
+
const borders = {
|
|
1506
|
+
left: lineChild(element, "a:lnL", part),
|
|
1507
|
+
right: lineChild(element, "a:lnR", part),
|
|
1508
|
+
top: lineChild(element, "a:lnT", part),
|
|
1509
|
+
bottom: lineChild(element, "a:lnB", part),
|
|
1510
|
+
tlToBr: lineChild(element, "a:lnTlToBr", part),
|
|
1511
|
+
blToTr: lineChild(element, "a:lnBlToTr", part)
|
|
1512
|
+
};
|
|
1513
|
+
const headers = firstChild(element, "a:headers");
|
|
1514
|
+
return {
|
|
1515
|
+
marL: coordinateOf(element, "marL", part),
|
|
1516
|
+
marR: coordinateOf(element, "marR", part),
|
|
1517
|
+
marT: coordinateOf(element, "marT", part),
|
|
1518
|
+
marB: coordinateOf(element, "marB", part),
|
|
1519
|
+
vert: enumOf(element, "vert", VERTICALS, part),
|
|
1520
|
+
anchor: enumOf(element, "anchor", ANCHORS, part),
|
|
1521
|
+
anchorCtr: boolOf(element, "anchorCtr", part),
|
|
1522
|
+
horzOverflow: enumOf(element, "horzOverflow", HORZ_OVERFLOWS, part),
|
|
1523
|
+
borders,
|
|
1524
|
+
fill: parseFill(element, part),
|
|
1525
|
+
headers: headers === void 0 ? [] : childElements(headers).filter((child) => child.qname === "a:header").map((child) => textContent(child)),
|
|
1526
|
+
node: element
|
|
1527
|
+
};
|
|
1528
|
+
}
|
|
1529
|
+
function parseCell(element, part) {
|
|
1530
|
+
const props = firstChild(element, "a:tcPr");
|
|
1531
|
+
return {
|
|
1532
|
+
gridSpan: intOf$1(element, "gridSpan", part) ?? 1,
|
|
1533
|
+
rowSpan: intOf$1(element, "rowSpan", part) ?? 1,
|
|
1534
|
+
hMerge: boolOf(element, "hMerge", part) ?? false,
|
|
1535
|
+
vMerge: boolOf(element, "vMerge", part) ?? false,
|
|
1536
|
+
id: attributeValue(element, "id") ?? null,
|
|
1537
|
+
text: parseTextBodyChild(element, part),
|
|
1538
|
+
props: props === void 0 ? void 0 : parseCellProps(props, part),
|
|
1539
|
+
node: element
|
|
1540
|
+
};
|
|
1541
|
+
}
|
|
1542
|
+
function parseRow(element, part) {
|
|
1543
|
+
return {
|
|
1544
|
+
h: required(element, "h", coordinateOf(element, "h", part), part),
|
|
1545
|
+
cells: childElements(element).filter((child) => child.qname === "a:tc").map((child) => parseCell(child, part)),
|
|
1546
|
+
node: element
|
|
1547
|
+
};
|
|
1548
|
+
}
|
|
1549
|
+
function parseColumn(element, part) {
|
|
1550
|
+
return {
|
|
1551
|
+
w: required(element, "w", coordinateOf(element, "w", part), part),
|
|
1552
|
+
node: element
|
|
1553
|
+
};
|
|
1554
|
+
}
|
|
1555
|
+
function parseStyleRef$1(element) {
|
|
1556
|
+
const id = firstChild(element, "a:tableStyleId");
|
|
1557
|
+
if (id !== void 0) return {
|
|
1558
|
+
kind: "id",
|
|
1559
|
+
id: textContent(id).trim()
|
|
1560
|
+
};
|
|
1561
|
+
const inline = firstChild(element, "a:tableStyle");
|
|
1562
|
+
return inline === void 0 ? void 0 : {
|
|
1563
|
+
kind: "inline",
|
|
1564
|
+
node: inline
|
|
1565
|
+
};
|
|
1566
|
+
}
|
|
1567
|
+
function parseTableProps(element, part) {
|
|
1568
|
+
const flag = (name) => boolOf(element, name, part) ?? false;
|
|
1569
|
+
return {
|
|
1570
|
+
rtl: flag("rtl"),
|
|
1571
|
+
firstRow: flag("firstRow"),
|
|
1572
|
+
firstCol: flag("firstCol"),
|
|
1573
|
+
lastRow: flag("lastRow"),
|
|
1574
|
+
lastCol: flag("lastCol"),
|
|
1575
|
+
bandRow: flag("bandRow"),
|
|
1576
|
+
bandCol: flag("bandCol"),
|
|
1577
|
+
fill: parseFill(element, part),
|
|
1578
|
+
effects: parseEffects(element),
|
|
1579
|
+
style: parseStyleRef$1(element),
|
|
1580
|
+
node: element
|
|
1581
|
+
};
|
|
1582
|
+
}
|
|
1583
|
+
/** An `a:tbl`. */
|
|
1584
|
+
function parseTable(element, part) {
|
|
1585
|
+
const props = firstChild(element, "a:tblPr");
|
|
1586
|
+
const grid = firstChild(element, "a:tblGrid");
|
|
1587
|
+
return {
|
|
1588
|
+
props: props === void 0 ? void 0 : parseTableProps(props, part),
|
|
1589
|
+
columns: grid === void 0 ? [] : childElements(grid).filter((child) => child.qname === "a:gridCol").map((child) => parseColumn(child, part)),
|
|
1590
|
+
rows: childElements(element).filter((child) => child.qname === "a:tr").map((child) => parseRow(child, part)),
|
|
1591
|
+
node: element
|
|
1592
|
+
};
|
|
1593
|
+
}
|
|
1594
|
+
/** The table of a `p:graphicFrame`, when its `a:graphicData` carries one. */
|
|
1595
|
+
function parseTableChild(frame, part) {
|
|
1596
|
+
const graphic = firstChild(frame, "a:graphic");
|
|
1597
|
+
const data = graphic === void 0 ? void 0 : firstChild(graphic, "a:graphicData");
|
|
1598
|
+
if (data === void 0 || attributeValue(data, "uri") !== "http://schemas.openxmlformats.org/drawingml/2006/table") return void 0;
|
|
1599
|
+
const table = firstChild(data, "a:tbl");
|
|
1600
|
+
return table === void 0 ? void 0 : parseTable(table, part);
|
|
1601
|
+
}
|
|
1602
|
+
//#endregion
|
|
1374
1603
|
//#region src/parse/sheet.ts
|
|
1375
1604
|
/**
|
|
1376
1605
|
* A slide, layout or master part into a `Sheet`; a theme part into a `Theme`.
|
|
@@ -1561,6 +1790,7 @@ function parseShape(element, kind, partName) {
|
|
|
1561
1790
|
prstGeom: prstGeom === void 0 ? void 0 : attributeValue(prstGeom, "prst") ?? "",
|
|
1562
1791
|
geometry: parseGeometry(spPr, partName),
|
|
1563
1792
|
text: parseTextBodyChild(element, partName),
|
|
1793
|
+
table: kind === "graphicFrame" ? parseTableChild(element, partName) : void 0,
|
|
1564
1794
|
children,
|
|
1565
1795
|
node: element
|
|
1566
1796
|
};
|
|
@@ -3037,6 +3267,6 @@ function resolveInsets(shape, sheet) {
|
|
|
3037
3267
|
};
|
|
3038
3268
|
}
|
|
3039
3269
|
//#endregion
|
|
3040
|
-
export { BUILTIN_TEXT_STYLES, COLOR_TRANSFORM_OPS, DEFAULT_PLACEHOLDER_IDX, DEFAULT_PLACEHOLDER_TYPE, LEVELS, MASTER_PLACEHOLDER_TYPES, MODEL_ERROR_CODES, ModelError, ORPHAN_RECT, PLACEHOLDER_TYPES, STYLE_MATRIX_OFFSET, TEXT_FLOOR, backgroundSheet, bucketOf, colorContextOf, colorMapOf, floorOf, inheritanceChain, isModelError, loadDocument, masterOf, masterPlaceholderType, matchInLayout, matchInMaster, normalizePlaceholder, parseBodyProps, parseBodyPropsChild, parseClrMap, parseColorChild, parseColorElement, parseDefaultTextStyle, parseEffects, parseFill, parseFillElement, parseGeometry, parseLine, parseLineElement, parseListStyle, parseParaProps, parseRunProps, parseSheet, parseTextBody, parseTextBodyChild, parseTextStyles, parseTheme, phClrOf, placeholders, requestedTypefaces, resolve, resolveAnchor, resolveAnchorCtr, resolveAppearance, resolveBackground, resolveBackgroundColor, resolveBody, resolveBulletAutoNum, resolveBulletBlip, resolveBulletChar, resolveBulletColor, resolveBulletFont, resolveBulletKind, resolveBulletSize, resolveColumns, resolveIndent, resolveInsets, resolveLatinTypeface, resolveMarginLeft, resolveOnSheet, resolveParagraph, resolveRun, resolveSize, resolveSolidFill, resolveTypeface, resolveTypefaceOf, resolveVertical, resolveWrap, resolveXfrm, schemeOf, sheetChain, styleMatrixEffects, styleMatrixFill, styleMatrixLine, styleMatrixTarget, textLevels, themeFontRef, themeOf };
|
|
3270
|
+
export { BUILTIN_TEXT_STYLES, COLOR_TRANSFORM_OPS, DEFAULT_PLACEHOLDER_IDX, DEFAULT_PLACEHOLDER_TYPE, INVENTED_COLUMN_WIDTH, LEVELS, MASTER_PLACEHOLDER_TYPES, MODEL_ERROR_CODES, ModelError, ORPHAN_RECT, PLACEHOLDER_TYPES, STYLE_MATRIX_OFFSET, TABLE_URI, TEXT_FLOOR, backgroundSheet, bucketOf, colorContextOf, colorMapOf, floorOf, inheritanceChain, isModelError, loadDocument, masterOf, masterPlaceholderType, matchInLayout, matchInMaster, normalizePlaceholder, parseBodyProps, parseBodyPropsChild, parseClrMap, parseColorChild, parseColorElement, parseDefaultTextStyle, parseEffects, parseFill, parseFillElement, parseGeometry, parseLine, parseLineElement, parseListStyle, parseParaProps, parseRunProps, parseSheet, parseTable, parseTableChild, parseTextBody, parseTextBodyChild, parseTextStyles, parseTheme, phClrOf, placeholders, requestedTypefaces, resolve, resolveAnchor, resolveAnchorCtr, resolveAppearance, resolveBackground, resolveBackgroundColor, resolveBody, resolveBulletAutoNum, resolveBulletBlip, resolveBulletChar, resolveBulletColor, resolveBulletFont, resolveBulletKind, resolveBulletSize, resolveColumns, resolveIndent, resolveInsets, resolveLatinTypeface, resolveMarginLeft, resolveOnSheet, resolveParagraph, resolveRun, resolveSize, resolveSolidFill, resolveTypeface, resolveTypefaceOf, resolveVertical, resolveWrap, resolveXfrm, schemeOf, sheetChain, styleMatrixEffects, styleMatrixFill, styleMatrixLine, styleMatrixTarget, tableGrid, textLevels, themeFontRef, themeOf };
|
|
3041
3271
|
|
|
3042
3272
|
//# sourceMappingURL=index.js.map
|