pptx-viewer-mcp 2.3.0 → 2.4.1
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 +12 -0
- package/dist/index.d.ts +16 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +242 -204
- package/dist/index.mjs +243 -205
- package/dist/mcp/index.js +255 -206
- package/dist/mcp/index.mjs +256 -207
- package/dist/schemas/index.d.ts +3 -0
- package/dist/schemas/index.d.ts.map +1 -1
- package/dist/schemas/index.js +13 -2
- package/dist/schemas/index.mjs +13 -2
- package/package.json +2 -2
package/dist/index.mjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { PptxHandler, hasTextProperties, resolveThemeColorRef, cloneElement as cloneElement$1, isTemplateElementId, makeStoreAwareId, reassignDescendantIds, groupElements as groupElements$1, ungroupElements as ungroupElements$1, TABLE_STYLE_PART_SEQUENCE, normalizeTableStyleGuid, createTableStyleEntry, addTableStyleToMap, deleteTableStyleFromMap, PptxMarkdownConverter, ThemePresets, getThemePreset, setChartType, setChartTitle, setChartGrouping, setChartLegend, setChartDataLabels, setChartAxis, setChartCategories, addChartSeries, removeChartSeries, updateChartSeriesValues, ChartBuilder, setChartDataPointStyle, setChartDataPointExplosion, setChartDataPointMarker, setChartDataPointLabel, setChartSeriesMarker, setChartSeriesTrendline, setChartSeriesErrorBars, setChartHelperLine, setChartColorMapOverride, listChartUserShapes, addChartUserShape, updateChartUserShape, removeChartUserShape, decomposeSmartArt, demoteSmartArtNode, promoteSmartArtNode, reorderSmartArtNode, updateSmartArtNodeText, removeSmartArtNode, addSmartArtNode, mergePresentation, diffPresentations, findPlaceholders, applyTemplate, getSectionForSlide, moveSlidesToSection, reorderSections, removeSection, addSection, SvgExporter, buildPptxJsonDocument, deserializePptxFromJson, applyImportedPptxData, replaceWithCustomGeometry, replaceShapeGeometry, setElementLocked, validatePptx, repairPptx, findLayoutByName, findLayoutByType } from 'pptx-viewer-core';
|
|
1
|
+
import { PptxHandler, hasTextProperties, resolveDisplayedChartTypeName, resolveThemeColorRef, cloneElement as cloneElement$1, isTemplateElementId, makeStoreAwareId, reassignDescendantIds, groupElements as groupElements$1, ungroupElements as ungroupElements$1, TABLE_STYLE_PART_SEQUENCE, normalizeTableStyleGuid, createTableStyleEntry, addTableStyleToMap, deleteTableStyleFromMap, PptxMarkdownConverter, ThemePresets, getThemePreset, setChartType, setChartTitle, setChartGrouping, setChartLegend, setChartDataLabels, setChartAxis, setChartCategories, addChartSeries, removeChartSeries, updateChartSeriesValues, ChartBuilder, setChartDataPointStyle, setChartDataPointExplosion, setChartDataPointMarker, setChartDataPointLabel, setChartSeriesMarker, setChartSeriesTrendline, setChartSeriesErrorBars, setChartHelperLine, setChartColorMapOverride, listChartUserShapes, addChartUserShape, updateChartUserShape, removeChartUserShape, decomposeSmartArt, demoteSmartArtNode, promoteSmartArtNode, reorderSmartArtNode, updateSmartArtNodeText, removeSmartArtNode, addSmartArtNode, mergePresentation, diffPresentations, findPlaceholders, applyTemplate, getSectionForSlide, moveSlidesToSection, reorderSections, removeSection, addSection, SvgExporter, buildPptxJsonDocument, deserializePptxFromJson, applyImportedPptxData, replaceWithCustomGeometry, replaceShapeGeometry, setElementLocked, validatePptx, repairPptx, findLayoutByName, findLayoutByType } from 'pptx-viewer-core';
|
|
2
2
|
export { PptxHandler } from 'pptx-viewer-core';
|
|
3
3
|
|
|
4
4
|
// src/execution.ts
|
|
@@ -165,8 +165,8 @@ function describeElement(el) {
|
|
|
165
165
|
base.cells = tbl.tableData.rows.map((row) => row.cells.map((cell) => cell.text ?? ""));
|
|
166
166
|
}
|
|
167
167
|
}
|
|
168
|
-
if (el.type === "chart") {
|
|
169
|
-
base.chartType = el.chartData
|
|
168
|
+
if (el.type === "chart" && el.chartData) {
|
|
169
|
+
base.chartType = resolveDisplayedChartTypeName(el.chartData);
|
|
170
170
|
}
|
|
171
171
|
if (el.type === "group") {
|
|
172
172
|
const grp = el;
|
|
@@ -394,6 +394,240 @@ function setCanvasSize(ctx, params) {
|
|
|
394
394
|
result: { canvasWidth: params.width, canvasHeight: params.height }
|
|
395
395
|
};
|
|
396
396
|
}
|
|
397
|
+
var ALT_TEXT_ELEMENT_TYPES = /* @__PURE__ */ new Set(["image", "picture", "table", "chart", "smartArt", "ole", "media", "text", "shape", "connector"]);
|
|
398
|
+
var TITLE_ELEMENT_TYPES = /* @__PURE__ */ new Set([
|
|
399
|
+
"table",
|
|
400
|
+
"chart",
|
|
401
|
+
"smartArt",
|
|
402
|
+
"ole",
|
|
403
|
+
"media",
|
|
404
|
+
"text",
|
|
405
|
+
"shape",
|
|
406
|
+
"connector"
|
|
407
|
+
]);
|
|
408
|
+
function applyElementAltText(el, altText) {
|
|
409
|
+
if (!ALT_TEXT_ELEMENT_TYPES.has(el.type)) {
|
|
410
|
+
throw new Error(
|
|
411
|
+
`Element '${el.id}' (${el.type}) does not support altText; only ${[...ALT_TEXT_ELEMENT_TYPES].join(", ")} elements do.`
|
|
412
|
+
);
|
|
413
|
+
}
|
|
414
|
+
el.altText = altText;
|
|
415
|
+
}
|
|
416
|
+
function applyElementTitle(el, title) {
|
|
417
|
+
if (!TITLE_ELEMENT_TYPES.has(el.type)) {
|
|
418
|
+
throw new Error(
|
|
419
|
+
`Element '${el.id}' (${el.type}) does not support title; only ${[...TITLE_ELEMENT_TYPES].join(", ")} elements do.`
|
|
420
|
+
);
|
|
421
|
+
}
|
|
422
|
+
el.title = title;
|
|
423
|
+
}
|
|
424
|
+
function updateElementStyle(ctx, params) {
|
|
425
|
+
const err = validateSlideIndex(params.slideIndex, ctx.pptxData.slides.length);
|
|
426
|
+
if (err) {
|
|
427
|
+
throw new Error(err);
|
|
428
|
+
}
|
|
429
|
+
const slide = ctx.pptxData.slides[params.slideIndex];
|
|
430
|
+
const el = slide.elements.find((e) => e.id === params.elementId);
|
|
431
|
+
if (!el) {
|
|
432
|
+
throw new Error(`Element '${params.elementId}' not found on slide ${params.slideIndex}.`);
|
|
433
|
+
}
|
|
434
|
+
if ("shapeStyle" in el) {
|
|
435
|
+
if (!el.shapeStyle) {
|
|
436
|
+
el.shapeStyle = {};
|
|
437
|
+
}
|
|
438
|
+
const ss = el.shapeStyle;
|
|
439
|
+
if (params.fillThemeColor !== void 0) {
|
|
440
|
+
ss.fillColorRef = params.fillThemeColor;
|
|
441
|
+
const resolved = resolveThemeColorRef(params.fillThemeColor, ctx.pptxData.themeColorMap);
|
|
442
|
+
if (params.fillColor !== void 0) {
|
|
443
|
+
ss.fillColor = params.fillColor;
|
|
444
|
+
} else if (resolved) {
|
|
445
|
+
ss.fillColor = resolved;
|
|
446
|
+
}
|
|
447
|
+
} else if (params.fillColor !== void 0) {
|
|
448
|
+
ss.fillColor = params.fillColor;
|
|
449
|
+
ss.fillColorRef = void 0;
|
|
450
|
+
}
|
|
451
|
+
if (params.fillMode !== void 0) {
|
|
452
|
+
ss.fillMode = params.fillMode;
|
|
453
|
+
}
|
|
454
|
+
if (params.fillGradientStops !== void 0) {
|
|
455
|
+
ss.fillGradientStops = params.fillGradientStops;
|
|
456
|
+
}
|
|
457
|
+
if (params.fillGradientAngle !== void 0) {
|
|
458
|
+
ss.fillGradientAngle = params.fillGradientAngle;
|
|
459
|
+
}
|
|
460
|
+
if (params.fillGradientType !== void 0) {
|
|
461
|
+
ss.fillGradientType = params.fillGradientType;
|
|
462
|
+
}
|
|
463
|
+
if (params.fillOpacity !== void 0) {
|
|
464
|
+
ss.fillOpacity = params.fillOpacity;
|
|
465
|
+
}
|
|
466
|
+
if (params.strokeThemeColor !== void 0) {
|
|
467
|
+
ss.strokeColorRef = params.strokeThemeColor;
|
|
468
|
+
const resolved = resolveThemeColorRef(params.strokeThemeColor, ctx.pptxData.themeColorMap);
|
|
469
|
+
if (params.strokeColor !== void 0) {
|
|
470
|
+
ss.strokeColor = params.strokeColor;
|
|
471
|
+
} else if (resolved) {
|
|
472
|
+
ss.strokeColor = resolved;
|
|
473
|
+
}
|
|
474
|
+
} else if (params.strokeColor !== void 0) {
|
|
475
|
+
ss.strokeColor = params.strokeColor;
|
|
476
|
+
ss.strokeColorRef = void 0;
|
|
477
|
+
}
|
|
478
|
+
if (params.strokeWidth !== void 0) {
|
|
479
|
+
ss.strokeWidth = params.strokeWidth;
|
|
480
|
+
}
|
|
481
|
+
if (params.strokeDash !== void 0) {
|
|
482
|
+
ss.strokeDash = params.strokeDash;
|
|
483
|
+
}
|
|
484
|
+
if (params.strokeOpacity !== void 0) {
|
|
485
|
+
ss.strokeOpacity = params.strokeOpacity;
|
|
486
|
+
}
|
|
487
|
+
if (params.shadowColor !== void 0) {
|
|
488
|
+
ss.shadowColor = params.shadowColor;
|
|
489
|
+
}
|
|
490
|
+
if (params.shadowBlur !== void 0) {
|
|
491
|
+
ss.shadowBlur = params.shadowBlur;
|
|
492
|
+
}
|
|
493
|
+
if (params.shadowOffsetX !== void 0) {
|
|
494
|
+
ss.shadowOffsetX = params.shadowOffsetX;
|
|
495
|
+
}
|
|
496
|
+
if (params.shadowOffsetY !== void 0) {
|
|
497
|
+
ss.shadowOffsetY = params.shadowOffsetY;
|
|
498
|
+
}
|
|
499
|
+
if (params.shadowOpacity !== void 0) {
|
|
500
|
+
ss.shadowOpacity = params.shadowOpacity;
|
|
501
|
+
}
|
|
502
|
+
if (params.glowColor !== void 0) {
|
|
503
|
+
ss.glowColor = params.glowColor;
|
|
504
|
+
}
|
|
505
|
+
if (params.glowRadius !== void 0) {
|
|
506
|
+
ss.glowRadius = params.glowRadius;
|
|
507
|
+
}
|
|
508
|
+
if (params.glowOpacity !== void 0) {
|
|
509
|
+
ss.glowOpacity = params.glowOpacity;
|
|
510
|
+
}
|
|
511
|
+
if (params.softEdgeRadius !== void 0) {
|
|
512
|
+
ss.softEdgeRadius = params.softEdgeRadius;
|
|
513
|
+
}
|
|
514
|
+
}
|
|
515
|
+
if (params.altText !== void 0) {
|
|
516
|
+
applyElementAltText(el, params.altText);
|
|
517
|
+
}
|
|
518
|
+
if (params.title !== void 0) {
|
|
519
|
+
applyElementTitle(el, params.title);
|
|
520
|
+
}
|
|
521
|
+
if (el.type === "image" || el.type === "picture") {
|
|
522
|
+
const img = el;
|
|
523
|
+
if (params.cropLeft !== void 0) {
|
|
524
|
+
img.cropLeft = params.cropLeft;
|
|
525
|
+
}
|
|
526
|
+
if (params.cropTop !== void 0) {
|
|
527
|
+
img.cropTop = params.cropTop;
|
|
528
|
+
}
|
|
529
|
+
if (params.cropRight !== void 0) {
|
|
530
|
+
img.cropRight = params.cropRight;
|
|
531
|
+
}
|
|
532
|
+
if (params.cropBottom !== void 0) {
|
|
533
|
+
img.cropBottom = params.cropBottom;
|
|
534
|
+
}
|
|
535
|
+
if (params.brightness !== void 0 || params.contrast !== void 0 || params.grayscale !== void 0) {
|
|
536
|
+
if (!img.imageEffects) {
|
|
537
|
+
img.imageEffects = {};
|
|
538
|
+
}
|
|
539
|
+
if (params.brightness !== void 0) {
|
|
540
|
+
img.imageEffects.brightness = params.brightness;
|
|
541
|
+
}
|
|
542
|
+
if (params.contrast !== void 0) {
|
|
543
|
+
img.imageEffects.contrast = params.contrast;
|
|
544
|
+
}
|
|
545
|
+
if (params.grayscale !== void 0) {
|
|
546
|
+
img.imageEffects.grayscale = params.grayscale;
|
|
547
|
+
}
|
|
548
|
+
}
|
|
549
|
+
}
|
|
550
|
+
return {
|
|
551
|
+
pptxData: ctx.pptxData,
|
|
552
|
+
dirty: true,
|
|
553
|
+
result: { elementId: params.elementId }
|
|
554
|
+
};
|
|
555
|
+
}
|
|
556
|
+
function runAccessibilityCheck(ctx) {
|
|
557
|
+
const issues = [];
|
|
558
|
+
for (let si = 0; si < ctx.pptxData.slides.length; si++) {
|
|
559
|
+
const slide = ctx.pptxData.slides[si];
|
|
560
|
+
let slideHasText = false;
|
|
561
|
+
for (const el of slide.elements) {
|
|
562
|
+
if (el.type === "image" || el.type === "picture") {
|
|
563
|
+
const img = el;
|
|
564
|
+
if (!img.altText) {
|
|
565
|
+
issues.push({
|
|
566
|
+
slideIndex: si,
|
|
567
|
+
elementId: el.id,
|
|
568
|
+
severity: "error",
|
|
569
|
+
message: `Image element '${el.id}' has no alt text.`
|
|
570
|
+
});
|
|
571
|
+
}
|
|
572
|
+
}
|
|
573
|
+
if (hasTextProperties(el)) {
|
|
574
|
+
const textEl = el;
|
|
575
|
+
slideHasText = true;
|
|
576
|
+
if (!textEl.text || textEl.text.trim() === "") {
|
|
577
|
+
issues.push({
|
|
578
|
+
slideIndex: si,
|
|
579
|
+
elementId: el.id,
|
|
580
|
+
severity: "info",
|
|
581
|
+
message: `Text element '${el.id}' is empty.`
|
|
582
|
+
});
|
|
583
|
+
}
|
|
584
|
+
const fs = textEl.textStyle?.fontSize;
|
|
585
|
+
if (fs !== void 0 && fs < 10) {
|
|
586
|
+
issues.push({
|
|
587
|
+
slideIndex: si,
|
|
588
|
+
elementId: el.id,
|
|
589
|
+
severity: "warning",
|
|
590
|
+
message: `Text element '${el.id}' has very small font size (${fs}pt < 10pt).`
|
|
591
|
+
});
|
|
592
|
+
}
|
|
593
|
+
const textColor = textEl.textStyle?.color?.toLowerCase();
|
|
594
|
+
const bgColor = slide.backgroundColor?.toLowerCase();
|
|
595
|
+
if (textColor && bgColor && textColor === bgColor) {
|
|
596
|
+
issues.push({
|
|
597
|
+
slideIndex: si,
|
|
598
|
+
elementId: el.id,
|
|
599
|
+
severity: "error",
|
|
600
|
+
message: `Text element '${el.id}' has same color as slide background (${textColor}).`
|
|
601
|
+
});
|
|
602
|
+
}
|
|
603
|
+
}
|
|
604
|
+
}
|
|
605
|
+
if (!slideHasText) {
|
|
606
|
+
issues.push({
|
|
607
|
+
slideIndex: si,
|
|
608
|
+
severity: "warning",
|
|
609
|
+
message: `Slide ${si + 1} contains no text elements.`
|
|
610
|
+
});
|
|
611
|
+
}
|
|
612
|
+
}
|
|
613
|
+
const errorCount = issues.filter((i) => i.severity === "error").length;
|
|
614
|
+
const warningCount = issues.filter((i) => i.severity === "warning").length;
|
|
615
|
+
const infoCount = issues.filter((i) => i.severity === "info").length;
|
|
616
|
+
return {
|
|
617
|
+
pptxData: ctx.pptxData,
|
|
618
|
+
dirty: false,
|
|
619
|
+
result: {
|
|
620
|
+
slideCount: ctx.pptxData.slides.length,
|
|
621
|
+
totalIssues: issues.length,
|
|
622
|
+
errorCount,
|
|
623
|
+
warningCount,
|
|
624
|
+
infoCount,
|
|
625
|
+
issues
|
|
626
|
+
}
|
|
627
|
+
};
|
|
628
|
+
}
|
|
629
|
+
|
|
630
|
+
// src/tools/element-tools.ts
|
|
397
631
|
function addElement(ctx, params) {
|
|
398
632
|
const err = validateSlideIndex(params.slideIndex, ctx.pptxData.slides.length);
|
|
399
633
|
if (err) {
|
|
@@ -573,6 +807,12 @@ function updateElement(ctx, params) {
|
|
|
573
807
|
if (params.flipV !== void 0) {
|
|
574
808
|
el.flipVertical = params.flipV;
|
|
575
809
|
}
|
|
810
|
+
if (params.altText !== void 0) {
|
|
811
|
+
applyElementAltText(el, params.altText);
|
|
812
|
+
}
|
|
813
|
+
if (params.title !== void 0) {
|
|
814
|
+
applyElementTitle(el, params.title);
|
|
815
|
+
}
|
|
576
816
|
if (hasTextProperties(el)) {
|
|
577
817
|
const textEl = el;
|
|
578
818
|
if (params.text !== void 0) {
|
|
@@ -1229,208 +1469,6 @@ function assignTableStyle(ctx, params) {
|
|
|
1229
1469
|
result: { elementId: params.elementId, styleId: normalizedId }
|
|
1230
1470
|
};
|
|
1231
1471
|
}
|
|
1232
|
-
function updateElementStyle(ctx, params) {
|
|
1233
|
-
const err = validateSlideIndex(params.slideIndex, ctx.pptxData.slides.length);
|
|
1234
|
-
if (err) {
|
|
1235
|
-
throw new Error(err);
|
|
1236
|
-
}
|
|
1237
|
-
const slide = ctx.pptxData.slides[params.slideIndex];
|
|
1238
|
-
const el = slide.elements.find((e) => e.id === params.elementId);
|
|
1239
|
-
if (!el) {
|
|
1240
|
-
throw new Error(`Element '${params.elementId}' not found on slide ${params.slideIndex}.`);
|
|
1241
|
-
}
|
|
1242
|
-
if ("shapeStyle" in el) {
|
|
1243
|
-
if (!el.shapeStyle) {
|
|
1244
|
-
el.shapeStyle = {};
|
|
1245
|
-
}
|
|
1246
|
-
const ss = el.shapeStyle;
|
|
1247
|
-
if (params.fillThemeColor !== void 0) {
|
|
1248
|
-
ss.fillColorRef = params.fillThemeColor;
|
|
1249
|
-
const resolved = resolveThemeColorRef(params.fillThemeColor, ctx.pptxData.themeColorMap);
|
|
1250
|
-
if (params.fillColor !== void 0) {
|
|
1251
|
-
ss.fillColor = params.fillColor;
|
|
1252
|
-
} else if (resolved) {
|
|
1253
|
-
ss.fillColor = resolved;
|
|
1254
|
-
}
|
|
1255
|
-
} else if (params.fillColor !== void 0) {
|
|
1256
|
-
ss.fillColor = params.fillColor;
|
|
1257
|
-
ss.fillColorRef = void 0;
|
|
1258
|
-
}
|
|
1259
|
-
if (params.fillMode !== void 0) {
|
|
1260
|
-
ss.fillMode = params.fillMode;
|
|
1261
|
-
}
|
|
1262
|
-
if (params.fillGradientStops !== void 0) {
|
|
1263
|
-
ss.fillGradientStops = params.fillGradientStops;
|
|
1264
|
-
}
|
|
1265
|
-
if (params.fillGradientAngle !== void 0) {
|
|
1266
|
-
ss.fillGradientAngle = params.fillGradientAngle;
|
|
1267
|
-
}
|
|
1268
|
-
if (params.fillGradientType !== void 0) {
|
|
1269
|
-
ss.fillGradientType = params.fillGradientType;
|
|
1270
|
-
}
|
|
1271
|
-
if (params.fillOpacity !== void 0) {
|
|
1272
|
-
ss.fillOpacity = params.fillOpacity;
|
|
1273
|
-
}
|
|
1274
|
-
if (params.strokeThemeColor !== void 0) {
|
|
1275
|
-
ss.strokeColorRef = params.strokeThemeColor;
|
|
1276
|
-
const resolved = resolveThemeColorRef(params.strokeThemeColor, ctx.pptxData.themeColorMap);
|
|
1277
|
-
if (params.strokeColor !== void 0) {
|
|
1278
|
-
ss.strokeColor = params.strokeColor;
|
|
1279
|
-
} else if (resolved) {
|
|
1280
|
-
ss.strokeColor = resolved;
|
|
1281
|
-
}
|
|
1282
|
-
} else if (params.strokeColor !== void 0) {
|
|
1283
|
-
ss.strokeColor = params.strokeColor;
|
|
1284
|
-
ss.strokeColorRef = void 0;
|
|
1285
|
-
}
|
|
1286
|
-
if (params.strokeWidth !== void 0) {
|
|
1287
|
-
ss.strokeWidth = params.strokeWidth;
|
|
1288
|
-
}
|
|
1289
|
-
if (params.strokeDash !== void 0) {
|
|
1290
|
-
ss.strokeDash = params.strokeDash;
|
|
1291
|
-
}
|
|
1292
|
-
if (params.strokeOpacity !== void 0) {
|
|
1293
|
-
ss.strokeOpacity = params.strokeOpacity;
|
|
1294
|
-
}
|
|
1295
|
-
if (params.shadowColor !== void 0) {
|
|
1296
|
-
ss.shadowColor = params.shadowColor;
|
|
1297
|
-
}
|
|
1298
|
-
if (params.shadowBlur !== void 0) {
|
|
1299
|
-
ss.shadowBlur = params.shadowBlur;
|
|
1300
|
-
}
|
|
1301
|
-
if (params.shadowOffsetX !== void 0) {
|
|
1302
|
-
ss.shadowOffsetX = params.shadowOffsetX;
|
|
1303
|
-
}
|
|
1304
|
-
if (params.shadowOffsetY !== void 0) {
|
|
1305
|
-
ss.shadowOffsetY = params.shadowOffsetY;
|
|
1306
|
-
}
|
|
1307
|
-
if (params.shadowOpacity !== void 0) {
|
|
1308
|
-
ss.shadowOpacity = params.shadowOpacity;
|
|
1309
|
-
}
|
|
1310
|
-
if (params.glowColor !== void 0) {
|
|
1311
|
-
ss.glowColor = params.glowColor;
|
|
1312
|
-
}
|
|
1313
|
-
if (params.glowRadius !== void 0) {
|
|
1314
|
-
ss.glowRadius = params.glowRadius;
|
|
1315
|
-
}
|
|
1316
|
-
if (params.glowOpacity !== void 0) {
|
|
1317
|
-
ss.glowOpacity = params.glowOpacity;
|
|
1318
|
-
}
|
|
1319
|
-
if (params.softEdgeRadius !== void 0) {
|
|
1320
|
-
ss.softEdgeRadius = params.softEdgeRadius;
|
|
1321
|
-
}
|
|
1322
|
-
}
|
|
1323
|
-
if (el.type === "image" || el.type === "picture") {
|
|
1324
|
-
const img = el;
|
|
1325
|
-
if (params.altText !== void 0) {
|
|
1326
|
-
img.altText = params.altText;
|
|
1327
|
-
}
|
|
1328
|
-
if (params.cropLeft !== void 0) {
|
|
1329
|
-
img.cropLeft = params.cropLeft;
|
|
1330
|
-
}
|
|
1331
|
-
if (params.cropTop !== void 0) {
|
|
1332
|
-
img.cropTop = params.cropTop;
|
|
1333
|
-
}
|
|
1334
|
-
if (params.cropRight !== void 0) {
|
|
1335
|
-
img.cropRight = params.cropRight;
|
|
1336
|
-
}
|
|
1337
|
-
if (params.cropBottom !== void 0) {
|
|
1338
|
-
img.cropBottom = params.cropBottom;
|
|
1339
|
-
}
|
|
1340
|
-
if (params.brightness !== void 0 || params.contrast !== void 0 || params.grayscale !== void 0) {
|
|
1341
|
-
if (!img.imageEffects) {
|
|
1342
|
-
img.imageEffects = {};
|
|
1343
|
-
}
|
|
1344
|
-
if (params.brightness !== void 0) {
|
|
1345
|
-
img.imageEffects.brightness = params.brightness;
|
|
1346
|
-
}
|
|
1347
|
-
if (params.contrast !== void 0) {
|
|
1348
|
-
img.imageEffects.contrast = params.contrast;
|
|
1349
|
-
}
|
|
1350
|
-
if (params.grayscale !== void 0) {
|
|
1351
|
-
img.imageEffects.grayscale = params.grayscale;
|
|
1352
|
-
}
|
|
1353
|
-
}
|
|
1354
|
-
}
|
|
1355
|
-
return {
|
|
1356
|
-
pptxData: ctx.pptxData,
|
|
1357
|
-
dirty: true,
|
|
1358
|
-
result: { elementId: params.elementId }
|
|
1359
|
-
};
|
|
1360
|
-
}
|
|
1361
|
-
function runAccessibilityCheck(ctx) {
|
|
1362
|
-
const issues = [];
|
|
1363
|
-
for (let si = 0; si < ctx.pptxData.slides.length; si++) {
|
|
1364
|
-
const slide = ctx.pptxData.slides[si];
|
|
1365
|
-
let slideHasText = false;
|
|
1366
|
-
for (const el of slide.elements) {
|
|
1367
|
-
if (el.type === "image" || el.type === "picture") {
|
|
1368
|
-
const img = el;
|
|
1369
|
-
if (!img.altText) {
|
|
1370
|
-
issues.push({
|
|
1371
|
-
slideIndex: si,
|
|
1372
|
-
elementId: el.id,
|
|
1373
|
-
severity: "error",
|
|
1374
|
-
message: `Image element '${el.id}' has no alt text.`
|
|
1375
|
-
});
|
|
1376
|
-
}
|
|
1377
|
-
}
|
|
1378
|
-
if (hasTextProperties(el)) {
|
|
1379
|
-
const textEl = el;
|
|
1380
|
-
slideHasText = true;
|
|
1381
|
-
if (!textEl.text || textEl.text.trim() === "") {
|
|
1382
|
-
issues.push({
|
|
1383
|
-
slideIndex: si,
|
|
1384
|
-
elementId: el.id,
|
|
1385
|
-
severity: "info",
|
|
1386
|
-
message: `Text element '${el.id}' is empty.`
|
|
1387
|
-
});
|
|
1388
|
-
}
|
|
1389
|
-
const fs = textEl.textStyle?.fontSize;
|
|
1390
|
-
if (fs !== void 0 && fs < 10) {
|
|
1391
|
-
issues.push({
|
|
1392
|
-
slideIndex: si,
|
|
1393
|
-
elementId: el.id,
|
|
1394
|
-
severity: "warning",
|
|
1395
|
-
message: `Text element '${el.id}' has very small font size (${fs}pt < 10pt).`
|
|
1396
|
-
});
|
|
1397
|
-
}
|
|
1398
|
-
const textColor = textEl.textStyle?.color?.toLowerCase();
|
|
1399
|
-
const bgColor = slide.backgroundColor?.toLowerCase();
|
|
1400
|
-
if (textColor && bgColor && textColor === bgColor) {
|
|
1401
|
-
issues.push({
|
|
1402
|
-
slideIndex: si,
|
|
1403
|
-
elementId: el.id,
|
|
1404
|
-
severity: "error",
|
|
1405
|
-
message: `Text element '${el.id}' has same color as slide background (${textColor}).`
|
|
1406
|
-
});
|
|
1407
|
-
}
|
|
1408
|
-
}
|
|
1409
|
-
}
|
|
1410
|
-
if (!slideHasText) {
|
|
1411
|
-
issues.push({
|
|
1412
|
-
slideIndex: si,
|
|
1413
|
-
severity: "warning",
|
|
1414
|
-
message: `Slide ${si + 1} contains no text elements.`
|
|
1415
|
-
});
|
|
1416
|
-
}
|
|
1417
|
-
}
|
|
1418
|
-
const errorCount = issues.filter((i) => i.severity === "error").length;
|
|
1419
|
-
const warningCount = issues.filter((i) => i.severity === "warning").length;
|
|
1420
|
-
const infoCount = issues.filter((i) => i.severity === "info").length;
|
|
1421
|
-
return {
|
|
1422
|
-
pptxData: ctx.pptxData,
|
|
1423
|
-
dirty: false,
|
|
1424
|
-
result: {
|
|
1425
|
-
slideCount: ctx.pptxData.slides.length,
|
|
1426
|
-
totalIssues: issues.length,
|
|
1427
|
-
errorCount,
|
|
1428
|
-
warningCount,
|
|
1429
|
-
infoCount,
|
|
1430
|
-
issues
|
|
1431
|
-
}
|
|
1432
|
-
};
|
|
1433
|
-
}
|
|
1434
1472
|
var MAX_REGEX_LEN = 200;
|
|
1435
1473
|
function hasNestedUnboundedQuantifier(pattern) {
|
|
1436
1474
|
return /\([^)]*[+*]\)[+*]/u.test(pattern);
|