【新增】 pptx验证考点修正
This commit is contained in:
@@ -17,7 +17,6 @@ public class PptxSaveReqVO {
|
||||
|
||||
@Schema(description = "节点名称", requiredMode = Schema.RequiredMode.REQUIRED, example = "芋道")
|
||||
@NotBlank(message = "节点名称不能为空")
|
||||
@Size(max = 30, message = "节点名称长度不能超过 30 个字符")
|
||||
private String name;
|
||||
/**
|
||||
* 类型
|
||||
|
@@ -17,7 +17,6 @@ public class WordSaveReqVO {
|
||||
|
||||
@Schema(description = "节点名称", requiredMode = Schema.RequiredMode.REQUIRED, example = "芋道")
|
||||
@NotBlank(message = "节点名称不能为空")
|
||||
@Size(max = 30, message = "节点名称长度不能超过 30 个字符")
|
||||
private String name;
|
||||
/**
|
||||
* 类型
|
||||
|
@@ -17,7 +17,6 @@ public class XlsxSaveReqVO {
|
||||
|
||||
@Schema(description = "节点名称", requiredMode = Schema.RequiredMode.REQUIRED, example = "芋道")
|
||||
@NotBlank(message = "节点名称不能为空")
|
||||
@Size(max = 30, message = "节点名称长度不能超过 30 个字符")
|
||||
private String name;
|
||||
/**
|
||||
* 类型
|
||||
|
@@ -38,6 +38,7 @@ public class JudgementWpsPptxServiceImpl implements JudgementWpsPptxService {
|
||||
String pathName = autoToolsService.downloadStudentFile(path, config.getValue());
|
||||
// 3、创建pptx考点tree
|
||||
PptxListReqVO pptxListReqVO = new PptxListReqVO();
|
||||
// 查询形状狭的所有数据
|
||||
pptxListReqVO.setBelongTo(0);
|
||||
// 3-1、查询段落的标签
|
||||
List<WpsPptxLinkDO> paragraphList = wpsPptxLinkMapper.selectList(pptxListReqVO);
|
||||
|
@@ -5,18 +5,14 @@ import org.apache.poi.xslf.usermodel.XSLFSlide;
|
||||
import org.apache.xmlbeans.XmlCursor;
|
||||
import org.apache.xmlbeans.XmlObject;
|
||||
import pc.exam.pp.module.judgement.dal.dataobject.wpspptx.WpsPptxLinkDO;
|
||||
import pc.exam.pp.module.judgement.dal.dataobject.wpsword.WpsWordLinkDO;
|
||||
import pc.exam.pp.module.judgement.utils.tree.TreeUtils;
|
||||
import pc.exam.pp.module.judgement.utils.wps_pptx.vo.PptxVO;
|
||||
import pc.exam.pp.module.judgement.utils.wps_word.vo.WordVO;
|
||||
|
||||
import java.io.FileInputStream;
|
||||
import java.io.FileNotFoundException;
|
||||
import java.io.IOException;
|
||||
import java.util.*;
|
||||
import java.util.regex.Matcher;
|
||||
import java.util.regex.Pattern;
|
||||
import java.util.stream.IntStream;
|
||||
|
||||
/**
|
||||
* @author REN
|
||||
@@ -33,6 +29,7 @@ public class WpsPptxUtils {
|
||||
int index = 0;
|
||||
// 获取了所有的幻灯片
|
||||
for (XSLFSlide slides : pptxXml.getSlides()){
|
||||
index += 1;
|
||||
String xmlText = slides.getXmlObject().xmlText();
|
||||
// 1-1、创建最全的命名空间
|
||||
Pattern pattern = Pattern.compile("xmlns:(\\w+)=\"([^\"]+)\"");
|
||||
@@ -55,13 +52,39 @@ public class WpsPptxUtils {
|
||||
String allPathx = xpathBuilder.toString();
|
||||
// 3、获取CTDocument对象
|
||||
XmlObject docXml = slides.getXmlObject();
|
||||
// 命名
|
||||
String typeName = "【第" + index + "页】";
|
||||
String englishName = "@" + index;
|
||||
for (WpsPptxLinkDO node : cSldTree) {
|
||||
traverseTreeAndQueryXml("111", pptxVOS, node.getName(), "123", allPathx, node, docXml, new ArrayList<>(), new ArrayList<>(), index, 1);
|
||||
// 4、查询形状下的所有数据 先查询有多少个形状
|
||||
XmlCursor xmlCursor = docXml.newCursor();
|
||||
xmlCursor.selectPath(allPathx + "//" + node.getName());
|
||||
System.out.println(xmlCursor.xmlText());
|
||||
// 获取p:sp形状下的数据
|
||||
int pIndex = 0;
|
||||
while (xmlCursor.toNextSelection()) {
|
||||
pIndex += 1;
|
||||
for (WpsPptxLinkDO anchor :node.getChildren()) {
|
||||
String spName = "【第" + pIndex + "个形状】";
|
||||
String englishSpName = "@" + pIndex;
|
||||
XmlCursor pXmlCursor = xmlCursor.getObject().newCursor();
|
||||
String nextString = allPathx + anchor.getName();
|
||||
pXmlCursor.selectPath(nextString);
|
||||
while (pXmlCursor.toNextSelection()) {
|
||||
XmlCursor pXmlCursors = pXmlCursor.getObject().newCursor();
|
||||
String textValue = pXmlCursors.getTextValue();
|
||||
PptxVO pptxVO = new PptxVO();
|
||||
pptxVO.setExamKeynote(englishName + englishSpName + anchor.getName()+ " " + textValue);
|
||||
pptxVO.setKeynoteChinese(typeName + spName + "【" + anchor.getToChinese() + "】" + textValue);
|
||||
pptxVOS.add(pptxVO);
|
||||
// System.out.println(typeName + spName + "【" + anchor.getToChinese() + "】" + textValue);
|
||||
}
|
||||
pXmlCursor.dispose();
|
||||
}
|
||||
// traverseTreeAndQueryXml(pptxVOS, typeName + "-第" + pIndex + "个形状", allPathx, node, pXmlObject, new ArrayList<>(), new ArrayList<>(), index, 1);
|
||||
}
|
||||
xmlCursor.dispose();
|
||||
}
|
||||
index += 1;
|
||||
// 2、解析文件内容
|
||||
XmlObject xml = slides.getXmlObject();
|
||||
System.out.println(index + "解析pptx文件内容: " + xml.xmlText());
|
||||
}
|
||||
|
||||
} catch (IOException e) {
|
||||
@@ -71,10 +94,8 @@ public class WpsPptxUtils {
|
||||
}
|
||||
|
||||
/**
|
||||
* @param type String 用来存放类型
|
||||
* @param pptxVOS List<PptxVO> 用来存放结果
|
||||
* @param firstTitle String 用来存放一级标题
|
||||
* @param text String 用来存放文本
|
||||
* @param xpath String 用来存放xpath
|
||||
* @param node WpsWordLinkDO 用来存放节点
|
||||
* @param currentXml XmlObject 用来存放当前xml
|
||||
@@ -83,100 +104,37 @@ public class WpsPptxUtils {
|
||||
* @param index int 用来存放索引
|
||||
* @param beginIndex int 用来存放开始索引
|
||||
*/
|
||||
public static void traverseTreeAndQueryXml(String type, List<PptxVO> pptxVOS, String firstTitle, String text, String xpath, WpsPptxLinkDO node, XmlObject currentXml, List<String> pathSoFar, List<String> pathChinese, int index, int beginIndex) {
|
||||
public static void traverseTreeAndQueryXml(List<PptxVO> pptxVOS, String firstTitle, String xpath, WpsPptxLinkDO node, XmlObject currentXml, List<String> pathSoFar, List<String> pathChinese, int index, int beginIndex) {
|
||||
// 到达参数节点,构造 XPath 路径查询它的值
|
||||
if (beginIndex == 1) {
|
||||
xpath += "./";
|
||||
}
|
||||
pathSoFar.add(node.getName());
|
||||
pathChinese.add(node.getToChinese() + index);
|
||||
if (beginIndex > 1) {
|
||||
pathSoFar.add(node.getName());
|
||||
pathChinese.add(node.getToChinese() + index);
|
||||
}
|
||||
|
||||
if (node.getType() == 1) {
|
||||
if (node.getType() == 1 || node.getType() == 2) {
|
||||
xpath += String.join("/", pathSoFar);
|
||||
try (XmlCursor cursors = currentXml.newCursor()) {
|
||||
System.out.println(cursors.xmlText());
|
||||
System.out.println(xpath);
|
||||
cursors.selectPath(xpath);
|
||||
if (cursors.toNextSelection()) {
|
||||
if (cursors.toNextSelection()) {
|
||||
String textValue = cursors.getTextValue();
|
||||
if (!Objects.equals(textValue, "")) {
|
||||
// 查找List里面是否已经存在相应文本的数据
|
||||
String finalText = text;
|
||||
int listIndex = IntStream.range(0, pptxVOS.size())
|
||||
.filter(i -> finalText.equals(pptxVOS.get(i).getWordText()))
|
||||
.findFirst()
|
||||
.orElse(-1);
|
||||
// 判断在段落内的样式,如果出现样式,向上兼容,直接再出现样式标签
|
||||
// System.out.println(xpath);
|
||||
if (xpath.indexOf("w:sectPr") > 0 && xpath.indexOf("w:p[") > 0) {
|
||||
// 说明出现了文本页面设置,需要进行向上绑定
|
||||
// 在获取当前的数组长度,获取上面的属性 遍历已经存在的数据
|
||||
int tindex = 0;
|
||||
for (PptxVO woVo : pptxVOS) {
|
||||
// 判断标识是否为false,,代表没有进行赋值
|
||||
if (!woVo.getIsTrue()) {
|
||||
PptxVO pptxVO = pptxVOS.get(tindex);
|
||||
pptxVO.setWordText(pptxVO.getWordText());
|
||||
woVo.setIsTrue(true);
|
||||
List<String> kchinese = woVo.getKeynoteChinese();
|
||||
List<String> examKeynote = woVo.getExamKeynote();
|
||||
examKeynote.add(String.join(" → ", pathSoFar) + ",value:" + textValue);
|
||||
kchinese.add(String.join(" → ", pathChinese) + ",值:" + textValue);
|
||||
pptxVO.setKeynoteChinese(kchinese);
|
||||
pptxVO.setExamKeynote(examKeynote);
|
||||
pptxVO.setType(type);
|
||||
pptxVOS.set(tindex, woVo);
|
||||
}
|
||||
tindex += 1;
|
||||
}
|
||||
} else if (listIndex < 0) {
|
||||
// 如果没有查询到了
|
||||
if (xpath.indexOf("w:sectPr[") > 0) {
|
||||
// 页面属性
|
||||
// 文本
|
||||
text = "页面属性";
|
||||
}
|
||||
if (!Objects.equals(text, "")) {
|
||||
if (!text.contains("MERGEFIELD")) {
|
||||
// 给标志符
|
||||
PptxVO pptxVO = new PptxVO();
|
||||
pptxVO.setWordText(text);
|
||||
// 创建list进行存放数据
|
||||
List<String> kchinese = new ArrayList<>();
|
||||
List<String> examKeynote = new ArrayList<>();
|
||||
examKeynote.add(String.join(" → ", pathSoFar) + ",value:" + textValue);
|
||||
kchinese.add(String.join(" → ", pathChinese) + ",值:" + textValue);
|
||||
// 组合完数据后进行存放数据
|
||||
pptxVO.setKeynoteChinese(kchinese);
|
||||
pptxVO.setExamKeynote(examKeynote);
|
||||
pptxVO.setIsTrue(false);
|
||||
pptxVO.setType(type);
|
||||
pptxVOS.add(pptxVO);
|
||||
}
|
||||
}
|
||||
} else { // 如果找到了
|
||||
PptxVO pptxVO = pptxVOS.get(listIndex);
|
||||
List<String> kchinese = pptxVO.getKeynoteChinese();
|
||||
List<String> examKeynote = pptxVO.getExamKeynote();
|
||||
examKeynote.add(String.join(" → ", pathSoFar) + ",value:" + textValue);
|
||||
kchinese.add(String.join(" → ", pathChinese) + ",值:" + textValue);
|
||||
pptxVO.setKeynoteChinese(kchinese);
|
||||
pptxVO.setExamKeynote(examKeynote);
|
||||
pptxVO.setIsTrue(false);
|
||||
pptxVO.setType(type);
|
||||
pptxVOS.remove(listIndex);
|
||||
pptxVOS.add(pptxVO);
|
||||
}
|
||||
// System.out.println("文本:" + text + " 参数路径:" + String.join(" → ", pathChinese) + ",值:" + text_value);
|
||||
}
|
||||
cursors.dispose();
|
||||
}
|
||||
}
|
||||
} else {
|
||||
for (WpsPptxLinkDO child : node.getChildren()) {
|
||||
traverseTreeAndQueryXml(type, pptxVOS, firstTitle, text, xpath, child, currentXml, new ArrayList<>(pathSoFar), new ArrayList<>(pathChinese), index,2);
|
||||
traverseTreeAndQueryXml(pptxVOS, firstTitle, xpath, child, currentXml, new ArrayList<>(pathSoFar), new ArrayList<>(pathChinese), index,2);
|
||||
}
|
||||
}
|
||||
pathSoFar.remove(pathSoFar.size() - 1);
|
||||
pathChinese.remove(pathChinese.size() - 1);
|
||||
if (!pathSoFar.isEmpty()) {
|
||||
pathSoFar.remove(pathSoFar.size() - 1);
|
||||
pathChinese.remove(pathChinese.size() - 1);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
@@ -8,19 +8,9 @@ import java.util.List;
|
||||
@Data
|
||||
public class PptxVO {
|
||||
|
||||
@Schema(description = "相关文本")
|
||||
private String wordText;
|
||||
|
||||
@Schema(description = "考试考点")
|
||||
private List<String> examKeynote;
|
||||
private String examKeynote;
|
||||
|
||||
@Schema(description = "考点汉化")
|
||||
private List<String> keynoteChinese;
|
||||
|
||||
@Schema(description = "是否有样式修饰")
|
||||
private Boolean isTrue;
|
||||
|
||||
@Schema(description = "类型")
|
||||
private String type;
|
||||
|
||||
private String keynoteChinese;
|
||||
}
|
||||
|
Reference in New Issue
Block a user