From cd7dec1ab31b07d448789894a49a132e27ad024e Mon Sep 17 00:00:00 2001 From: dlaren Date: Wed, 13 Aug 2025 20:46:01 +0800 Subject: [PATCH] =?UTF-8?q?=E3=80=90=E6=96=B0=E5=A2=9E=E3=80=91=20?= =?UTF-8?q?=E4=BD=BF=E7=94=A8pptx4j=20=E8=8E=B7=E5=8F=96ppt=E6=96=87?= =?UTF-8?q?=E4=BB=B6=E7=9A=84=E8=80=83=E7=82=B9=EF=BC=88=E5=BD=A2=E7=8A=B6?= =?UTF-8?q?=EF=BC=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../admin/AutoWps/vo/WpsSlideInfoVo.java | 11 +- .../wps_pptx/JudgementWpsPptxServiceImpl.java | 2 +- .../utils/wps_pptx/pptx4j/Shape.java | 247 ++++++++++++++++++ .../wps_pptx/pptx4j/SlideConversion.java | 10 +- .../utils/wps_pptx/pptx4j/SlideMaster.java | 72 +++-- .../utils/wps_pptx/pptx4j/SlideUtils.java | 113 ++++++++ 6 files changed, 431 insertions(+), 24 deletions(-) create mode 100644 exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/utils/wps_pptx/pptx4j/Shape.java create mode 100644 exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/utils/wps_pptx/pptx4j/SlideUtils.java diff --git a/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/controller/admin/AutoWps/vo/WpsSlideInfoVo.java b/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/controller/admin/AutoWps/vo/WpsSlideInfoVo.java index 14302193..17a59b12 100644 --- a/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/controller/admin/AutoWps/vo/WpsSlideInfoVo.java +++ b/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/controller/admin/AutoWps/vo/WpsSlideInfoVo.java @@ -4,13 +4,18 @@ import lombok.Data; @Data public class WpsSlideInfoVo { + // 幻灯片位置(第几张幻灯片) + private String slideIndex; + + // 形状位置,只有在shape 形状(不包含图片) shapePic 形状图片 + private String shapeIndex; + + // 形状类型 slide 幻灯片设置 shape 形状(不包含图片) shapePic 形状图片 presentation 总幻灯片设置 + private String type; // 大类名称 private String firstName; - // 序号 - private String index; - // 方法名称 private String function; diff --git a/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/service/wps_pptx/JudgementWpsPptxServiceImpl.java b/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/service/wps_pptx/JudgementWpsPptxServiceImpl.java index b0f903ea..15465bf8 100644 --- a/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/service/wps_pptx/JudgementWpsPptxServiceImpl.java +++ b/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/service/wps_pptx/JudgementWpsPptxServiceImpl.java @@ -19,7 +19,7 @@ public class JudgementWpsPptxServiceImpl implements JudgementWpsPptxService { @Override public List slideMaster(List wpsSlideInfoVos, MultipartFile file) throws Exception { - return SlideMaster.slideMaster(file); + return SlideMaster.slideMaster(wpsSlideInfoVos, file); } /** diff --git a/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/utils/wps_pptx/pptx4j/Shape.java b/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/utils/wps_pptx/pptx4j/Shape.java new file mode 100644 index 00000000..228457f6 --- /dev/null +++ b/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/utils/wps_pptx/pptx4j/Shape.java @@ -0,0 +1,247 @@ +package pc.exam.pp.module.judgement.utils.wps_pptx.pptx4j; + +import org.docx4j.dml.*; + +public class Shape { + + // 大小 - 高度 + public static String getShapeSizeHeight(org.pptx4j.pml.Shape sp) { + CTTransform2D xfrm = sp.getSpPr().getXfrm(); + // 获取位置和尺寸(单位 EMU,1英寸=914400 EMU,1cm≈360000 EMU) + CTPositiveSize2D ext = xfrm.getExt(); // 尺寸 + double heightPt = emuToPt(ext.getCy()); + return String.valueOf(heightPt); + } + // 大小 - 宽度 + public static String getShapeSizeWidthPt(org.pptx4j.pml.Shape sp) { + CTTransform2D xfrm = sp.getSpPr().getXfrm(); + // 获取位置和尺寸(单位 EMU,1英寸=914400 EMU,1cm≈360000 EMU) + CTPositiveSize2D ext = xfrm.getExt(); // 尺寸 + double widthPt = emuToPt(ext.getCx()); + return String.valueOf(widthPt); + } + // 大小 - 锁定纵横比 + public static String getShapeSizeLockAspectRatio(org.pptx4j.pml.Shape sp) { + CTTransform2D xfrm = sp.getSpPr().getXfrm(); + // 获取位置和尺寸(单位 EMU,1英寸=914400 EMU,1cm≈360000 EMU) + CTPositiveSize2D ext = xfrm.getExt(); // 尺寸 + Boolean lockAspectRatio = null; + if (sp.getSpPr().getPrstGeom() != null && + sp.getSpPr().getPrstGeom().getAvLst() != null) { + // 这个部分一般不会直接提供锁定横纵比,要看 spPr.getExtLst() + if (sp.getSpPr().getExtLst() != null) { + // pptx4j 没有直接的 getter,要自己解析 XML + String xml = sp.getSpPr().getExtLst().toString(); + if (xml.contains("lockAspectRatio=\"1\"") || xml.contains("lockAspectRatio=\"true\"")) { + lockAspectRatio = true; + } else if (xml.contains("lockAspectRatio=\"0\"") || xml.contains("lockAspectRatio=\"false\"")) { + lockAspectRatio = false; + } + } + } + return String.valueOf(lockAspectRatio); + } + // EMU 转 pt + private static double emuToPt(long emu) { + return emu / 12700.0; + } + + // 位置 水平位置 + public static String getShapePositionLeft(org.pptx4j.pml.Shape sp) { + CTTransform2D xfrm = sp.getSpPr().getXfrm(); + if (xfrm != null) { + long x = xfrm.getOff().getX(); // 水平位置(EMU) + return String.valueOf(x / 9525.0); + } + return ""; + } + // 位置 垂直位置 + public static String getShapePositionTop(org.pptx4j.pml.Shape sp) { + CTTransform2D xfrm = sp.getSpPr().getXfrm(); + if (xfrm != null) { + long y = xfrm.getOff().getY(); // 垂直位置(EMU) + return String.valueOf(y / 9525.0); + } + return ""; + } + + // 形状填充 填充方式 + public static String getShapeFillType(org.pptx4j.pml.Shape sp) { + CTShapeProperties spPr = sp.getSpPr(); + return SlideUtils.getFillType(spPr); + } + + // 形状填充 纯色填充-颜色 + public static String getShapeFillSolidColor(org.pptx4j.pml.Shape sp) { + CTShapeProperties spPr = sp.getSpPr(); + if (spPr != null && spPr.getSolidFill() != null) { + return SlideUtils.getSolidFillColor(spPr.getSolidFill()); + } + return ""; + } + + // 形状填充 渐变填充-效果 + public static String getShapeFillGradientType(org.pptx4j.pml.Shape sp) { + CTShapeProperties spPr = sp.getSpPr(); + + if (spPr != null && spPr.getGradFill() != null) { + System.out.println("形状: " + sp.getNvSpPr().getCNvPr().getName()); + return SlideUtils.printGradientFill(spPr.getGradFill()); + } + return ""; + } + + // 形状填充 图片填充-效果 + public static String getShapeFillPictureType(org.pptx4j.pml.Shape sp){ + CTShapeProperties spPr = sp.getSpPr(); + + if (spPr != null && spPr.getBlipFill() != null) { + System.out.println("形状: " + sp.getNvSpPr().getCNvPr().getName()); + return SlideUtils.printImageFill(spPr.getBlipFill()); + } + return ""; + } + + // 形状填充 纹理填充-效果 + public static String getShapeFillTextureType(org.pptx4j.pml.Shape sp) { + CTShapeProperties spPr = sp.getSpPr(); + if (spPr != null && spPr.getPattFill() != null) { + return SlideUtils.printPatternFill(spPr.getPattFill()); + } + return ""; + } + + // 形状填充 图案填充-效果 + public static String getShapeFillPatternType(org.pptx4j.pml.Shape sp) { + CTShapeProperties spPr = sp.getSpPr(); + if (spPr != null && spPr.getPattFill() != null) { + return spPr.getPattFill().getPrst().value(); + } + return ""; + } + + // 形状填充 幻灯片背景填充-效果 + public static String getShapeFillSlideBackgroundType(org.pptx4j.pml.Shape sp) { + return ""; + } + + // 形状填充 填充透明度 + public static String getShapeFillOpacity(org.pptx4j.pml.Shape sp) { + return ""; + } + + // 形状线条 绘制 + public static String getShapeLineDraw(org.pptx4j.pml.Shape sp) { + CTShapeProperties spPr = sp.getSpPr(); + + if (spPr != null && spPr.getLn() != null) { + CTLineProperties ln = spPr.getLn(); + + // 宽度(EMU -> pt) + double widthPt = ln.getW() / 12700.0; + System.out.println("形状: " + sp.getNvSpPr().getCNvPr().getName()); + System.out.println("线宽: " + widthPt + " pt"); + + // 颜色 + if (ln.getSolidFill() != null && ln.getSolidFill().getSrgbClr() != null) { + CTSRgbColor rgb = ln.getSolidFill().getSrgbClr(); + System.out.println("线条颜色: #" + rgb.getVal()); + } + + // 虚线样式 + if (ln.getPrstDash() != null) { + System.out.println("线型: " + ln.getPrstDash().getVal().value()); + } + + // 端点样式 + if (ln.getCap() != null) { + System.out.println("端点: " + ln.getCap().value()); + } + return "是"; + } + return ""; + } + + // 形状线条 线条颜色 + public static String getShapeLineColor(org.pptx4j.pml.Shape sp) { + CTShapeProperties spPr = sp.getSpPr(); + + if (spPr != null && spPr.getLn() != null) { + CTLineProperties ln = spPr.getLn(); + // 颜色 + if (ln.getSolidFill() != null && ln.getSolidFill().getSrgbClr() != null) { + CTSRgbColor rgb = ln.getSolidFill().getSrgbClr(); + return rgb.getVal(); + } + } + return ""; + } + + // 形状线条 线条宽度 + public static String getShapeLineWidth(org.pptx4j.pml.Shape sp) { + CTShapeProperties spPr = sp.getSpPr(); + + if (spPr != null && spPr.getLn() != null) { + CTLineProperties ln = spPr.getLn(); + // 宽度(EMU -> pt) + double widthPt = ln.getW() / 12700.0; + return String.valueOf(widthPt); + } + return ""; + } + + // 形状线条 透明度 + public static String getShapeLineOpacity(org.pptx4j.pml.Shape sp) { + + return ""; + } + + // 形状线条 复合类型 + public static String getStrokeCompound(org.pptx4j.pml.Shape sp) { + if (sp == null || sp.getSpPr() == null) return "未定义"; + CTShapeProperties spPr = sp.getSpPr(); + CTLineProperties ln = spPr.getLn(); + if (ln == null) return "未定义"; + + STCompoundLine cmpd = ln.getCmpd(); // 可能为 null + String v = (cmpd != null) ? cmpd.value() : "sng"; // 默认单线 + switch (v) { + case "dbl": return "双线 (dbl)"; + case "thickThin": return "粗-细双线 (thickThin)"; + case "thinThick": return "细-粗双线 (thinThick)"; + case "tri": return "三重线 (tri)"; + case "sng": + default: return "单线 (sng)"; + } + } + + // 形状线条 短划线类型 + public static String getStrokeDash(org.pptx4j.pml.Shape sp) { + if (sp == null || sp.getSpPr() == null) return "solid"; + CTShapeProperties spPr = sp.getSpPr(); + CTLineProperties ln = spPr.getLn(); + if (ln == null) return "solid"; + + // 1) 预设短划线 + if (ln.getPrstDash() != null && ln.getPrstDash().getVal() != null) { + STPresetLineDashVal val = ln.getPrstDash().getVal(); + return SlideUtils.mapPreset(val); + } + + // 2) 自定义短划线 + if (ln.getCustDash() != null && ln.getCustDash().getDs() != null && !ln.getCustDash().getDs().isEmpty()) { + StringBuilder sb = new StringBuilder("custom "); + for (CTDashStop ds : ln.getCustDash().getDs()) { + int d = ds.getD(); // dash length(相对线宽的比例单位) + int sps = ds.getSp(); // space length(相对线宽的比例单位) + sb.append("[d=").append(d).append(", sps=").append(sps).append("] "); + } + return sb.toString().trim(); + } + + // 3) 未设置 → 视为实线 + return "solid"; + } + + +} diff --git a/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/utils/wps_pptx/pptx4j/SlideConversion.java b/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/utils/wps_pptx/pptx4j/SlideConversion.java index 0e16f2bf..1ba31d79 100644 --- a/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/utils/wps_pptx/pptx4j/SlideConversion.java +++ b/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/utils/wps_pptx/pptx4j/SlideConversion.java @@ -26,7 +26,7 @@ public class SlideConversion { for (XSLFSlide slides : pptxXml.getSlides()){ index += 1; String secondId = getStringRandom(); - setSlideDataInfo(secondId, firstId, "第"+index+"页", "p:sld", String.valueOf(index), true, dataInfoVOS); + setSlideDataInfo(secondId, firstId, "第"+index+"页", "sld", String.valueOf(index), true, dataInfoVOS); // 第三层 String thirdId = getStringRandom(); int indexCnvPr = 1; @@ -39,7 +39,7 @@ public class SlideConversion { if (cNvPrXml.toNextSelection()) { String name = cNvPrXml.getTextValue(); String fourId = getStringRandom(); - setSlideDataInfo(fourId, secondId, "形状"+indexCnvPr+"->"+name, "slides", String.valueOf(indexCnvPr), true, dataInfoVOS); + setSlideDataInfo(fourId, secondId, "形状"+indexCnvPr+"->"+name, "shape", String.valueOf(indexCnvPr), true, dataInfoVOS); indexCnvPr += 1; } } @@ -49,15 +49,15 @@ public class SlideConversion { int indexCnvPrPic = 1; while (picCursor.toNextSelection()) { String fourId = getStringRandom(); - setSlideDataInfo(fourId, secondId, "图像"+indexCnvPrPic+"->图像", "p:pic", String.valueOf(indexCnvPrPic), true, dataInfoVOS); + setSlideDataInfo(fourId, secondId, "图像"+indexCnvPrPic+"->图像", "shapePic", String.valueOf(indexCnvPrPic), true, dataInfoVOS); indexCnvPrPic += 1; } } // 设置 String firstIds = getStringRandom(); - setSlideDataInfo(firstIds, "", "设置", "p:presentation", String.valueOf(0), false, dataInfoVOS); + setSlideDataInfo(firstIds, "", "设置", "presentation", String.valueOf(0), false, dataInfoVOS); String secondIds = getStringRandom(); - setSlideDataInfo(secondIds, firstIds, "幻灯片设置", "p:presentation", String.valueOf(0), true, dataInfoVOS); + setSlideDataInfo(secondIds, firstIds, "幻灯片设置", "presentation", String.valueOf(0), true, dataInfoVOS); // 母版 // String dFirstId = getStringRandom(); diff --git a/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/utils/wps_pptx/pptx4j/SlideMaster.java b/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/utils/wps_pptx/pptx4j/SlideMaster.java index b1fcc123..221a127c 100644 --- a/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/utils/wps_pptx/pptx4j/SlideMaster.java +++ b/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/utils/wps_pptx/pptx4j/SlideMaster.java @@ -3,44 +3,86 @@ package pc.exam.pp.module.judgement.utils.wps_pptx.pptx4j; import org.docx4j.openpackaging.exceptions.Docx4JException; import org.docx4j.openpackaging.packages.OpcPackage; import org.docx4j.openpackaging.packages.PresentationMLPackage; +import org.docx4j.openpackaging.packages.WordprocessingMLPackage; import org.docx4j.openpackaging.parts.PresentationML.SlidePart; +import org.docx4j.openpackaging.parts.WordprocessingML.NumberingDefinitionsPart; +import org.docx4j.openpackaging.parts.WordprocessingML.StyleDefinitionsPart; +import org.docx4j.wml.P; import org.pptx4j.pml.GroupShape; import org.pptx4j.pml.Shape; import org.springframework.web.multipart.MultipartFile; +import pc.exam.pp.module.judgement.controller.admin.AutoWps.vo.WpsSlideInfoVo; import pc.exam.pp.module.judgement.utils.wps_pptx.pptx4j.vo.JudgementSlidesVO; +import pc.exam.pp.module.judgement.utils.wps_word.docx4j.paragraph.Paragraphs; import java.io.IOException; import java.io.InputStream; +import java.lang.reflect.Method; import java.util.ArrayList; import java.util.List; public class SlideMaster { - public static List slideMaster(MultipartFile file) throws IOException, Docx4JException { + public static List slideMaster(List wpsSlideInfoVos, MultipartFile file) throws IOException, Docx4JException { List judgementSlidesVOS = new ArrayList<>(); // 1、获取想要判断的文件地址(文件流) try (InputStream inputStream = file.getInputStream()) { // 加载 .pptx 文件 PresentationMLPackage ppt = (PresentationMLPackage) OpcPackage.load(inputStream); - // 你可以在这里处理 ppt,比如读取文字、页数等 - List slideParts = ppt.getMainPresentationPart().getSlideParts(); - int slideIndex = 1; - for (SlidePart slidePart : slideParts) { - // 获取幻灯片内容 - System.out.println("========== 幻灯片 " + slideIndex++ + " =========="); - // 遍历 shape tree 中的 sp(shape)元素 - GroupShape spTree = slidePart.getJaxbElement().getCSld().getSpTree(); - List shapes = spTree.getSpOrGrpSpOrGraphicFrame(); - for (Object shapeObj : shapes) { - if (shapeObj instanceof Shape) { - Shape shape = (Shape) shapeObj; - System.out.println("Shape name: " + shape.getNvSpPr().getCNvPr().getName()); + for (WpsSlideInfoVo wpsSlideInfoVo : wpsSlideInfoVos) { + // 幻灯片位置(第几张幻灯片) + String slideIndex = wpsSlideInfoVo.getSlideIndex(); + String shapeIndex = wpsSlideInfoVo.getShapeIndex(); + // 形状类型 slide 幻灯片设置 shape 形状(不包含图片) shapePic 形状图片 presentation 总幻灯片设置 + String type = wpsSlideInfoVo.getType(); + // 大类名称 + String firstName = wpsSlideInfoVo.getFirstName(); + // 方法名称 + String function = wpsSlideInfoVo.getFunction(); + // 考点名称 + String examName = wpsSlideInfoVo.getExamName(); + // 考点代码 + String examCode = wpsSlideInfoVo.getExamCode(); + // 方式方法 + String method = wpsSlideInfoVo.getMethod(); + if (type.equals("shape")) { + // 查询幻灯片图片 + List slideParts = ppt.getMainPresentationPart().getSlideParts(); + int slideIndexFoFile = 1; + for (SlidePart slidePart : slideParts) { + // 获取幻灯片内容 + slideIndexFoFile++; + if (slideIndex.equals(String.valueOf(slideIndexFoFile))) { + // 查询幻灯片 + // 遍历 shape tree 中的 sp(shape)元素 + GroupShape spTree = slidePart.getJaxbElement().getCSld().getSpTree(); + List shapes = spTree.getSpOrGrpSpOrGraphicFrame(); + int shapeIndexFoFile = 1; + for (Object shapeObj : shapes) { + shapeIndexFoFile++; + if (shapeObj instanceof Shape) { + Shape shape = (Shape) shapeObj; + if (shapeIndex.equals(String.valueOf(shapeIndexFoFile))) { + // 查询出具体想要查询哪个段落的数据 + // 目标对象 + Shape shapeFunction = new Shape(); + // 获取参数中类型的定义 + Class[] paramTypes = {Shape.class}; + // 带参数的方法调用示例 + Method methodWithArgs = shapeFunction.getClass().getMethod(function, paramTypes); + // 实际参数值 + Object[] arguments = {shape}; + String value = (String) methodWithArgs.invoke(shapeFunction, arguments); + System.out.println(value); + } + } + } + } } } } - } catch (Exception e) { e.printStackTrace(); } diff --git a/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/utils/wps_pptx/pptx4j/SlideUtils.java b/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/utils/wps_pptx/pptx4j/SlideUtils.java new file mode 100644 index 00000000..d468677a --- /dev/null +++ b/exam-module-judgement/exam-module-judgement-biz/src/main/java/pc/exam/pp/module/judgement/utils/wps_pptx/pptx4j/SlideUtils.java @@ -0,0 +1,113 @@ +package pc.exam.pp.module.judgement.utils.wps_pptx.pptx4j; + +import org.docx4j.dml.*; +import org.docx4j.openpackaging.parts.PresentationML.SlidePart; + +public class SlideUtils { + public static String getFillType(CTShapeProperties spPr) { + if (spPr == null) return "未知"; + + if (spPr.getNoFill() != null) { + return "无填充"; + } + if (spPr.getSolidFill() != null) { + return "纯色填充"; + } + if (spPr.getGradFill() != null) { + return "渐变填充"; + } + if (spPr.getBlipFill() != null) { + return "图片填充"; + } + if (spPr.getPattFill() != null) { + return "图案填充"; + } + return "其他/未知"; + } + + // 形状填充 纯色填充-颜色 + public static String getSolidFillColor(CTSolidColorFillProperties solidFill) { + if (solidFill.getSrgbClr() != null) { + // 直接 RGB 颜色 + CTSRgbColor rgb = solidFill.getSrgbClr(); + return "#" + rgb.getVal(); // 已经是16进制字符串 + } + if (solidFill.getSchemeClr() != null) { + // 主题色(这里只返回主题色名称) + CTSchemeColor scheme = solidFill.getSchemeClr(); + return "主题色: " + scheme.getVal().value(); + } + if (solidFill.getPrstClr() != null) { + // 预设色(只返回名字) + CTPresetColor preset = solidFill.getPrstClr(); + return "预设色: " + preset.getVal().value(); + } + return "未知颜色"; + } + + public static String printGradientFill(CTGradientFillProperties gradFill) { + // 渐变点 + CTGradientStopList gsList = gradFill.getGsLst(); + if (gsList != null) { + for (CTGradientStop gs : gsList.getGs()) { + String color = "未知颜色"; + if (gs.getSrgbClr() != null) { + CTSRgbColor rgb = gs.getSrgbClr(); + color = "#" + rgb.getVal(); + } else if (gs.getSchemeClr() != null) { + CTSchemeColor scheme = gs.getSchemeClr(); + color = "主题色: " + scheme.getVal().value(); + } + return "渐变点 位置: " + (gs.getPos() / 1000.0) + "% 颜色: " + color; + } + } + + // 渐变类型(线性 / 放射) + if (gradFill.getLin() != null) { + double angle = gradFill.getLin().getAng() / 60000.0; // 单位换成度 + return "渐变类型: 线性 角度: " + angle + "°"; + } else if (gradFill.getPath() != null) { + return "渐变类型: " + gradFill.getPath().getPath().value(); + } + return "未知渐变类型"; + } + + public static String printImageFill(CTBlipFillProperties blipFill) { + // 填充模式 + CTTileInfoProperties tile = blipFill.getTile(); + if (tile != null) { + return "填充模式: 平铺"; + } + + CTStretchInfoProperties stretch = blipFill.getStretch(); + if (stretch != null) { + return "填充模式: 拉伸"; + } + return "未知填充模式"; + } + + public static String printPatternFill(CTPatternFillProperties pattFill) { + // 预设纹理/图案名称 + return pattFill.getPrst().value(); + } + + public static String mapPreset(STPresetLineDashVal v) { + // 常见值:solid, dash, dot, dashDot, lgDash, lgDashDot, lgDashDotDot, + // sysDash, sysDot, sysDashDot, sysDashDotDot + switch (v) { + case SOLID: return "solid"; + case DASH: return "dash"; + case DOT: return "dot"; + case DASH_DOT: return "dashDot"; + case LG_DASH: return "lgDash"; + case LG_DASH_DOT: return "lgDashDot"; + case LG_DASH_DOT_DOT:return "lgDashDotDot"; + case SYS_DASH: return "sysDash"; + case SYS_DOT: return "sysDot"; + case SYS_DASH_DOT: return "sysDashDot"; + case SYS_DASH_DOT_DOT:return "sysDashDotDot"; + default: return v.value(); // 兜底:返回原枚举字符串 + } + } + +}