Замена всего текста в powerpoint с помощью Apache POI - PullRequest
0 голосов
/ 24 сентября 2018

Я посмотрел документацию по Apache POI и создал функцию, которая редактирует весь текст в powerpoint.Функция хорошо работает при замене текстов на слайдах, но не текстов, найденных в сгруппированных текстовых полях.Есть ли отдельный объект, который обрабатывает сгруппированные элементы?

private static void redactText(XMLSlideShow ppt) {
    for (XSLFSlide slide : ppt.getSlides()) {
        System.out.println("REDACT Slide: " + slide.getTitle());

        XSLFTextShape[] shapes = slide.getPlaceholders();

        for (XSLFTextShape textShape : shapes) {

            List<XSLFTextParagraph> textparagraphs = textShape.getTextParagraphs();

            for (XSLFTextParagraph para : textparagraphs) {

                List<XSLFTextRun> textruns = para.getTextRuns();

                for (XSLFTextRun incomingTextRun : textruns) {

                    String text = incomingTextRun.getRawText();

                    System.out.println(text);

                    if (text.toLowerCase().contains("test")) {

                        String newText = text.replaceAll("(?i)" + "test", "XXXXXXXX");

                        incomingTextRun.setText(newText);

                    }
                }
            }

        }
    }
}

Ответы [ 2 ]

0 голосов
/ 13 мая 2019

Если вам не нравится подход замены через Xml напрямую, можно выполнить итерации по всем слайдам и их формам.Если фигура XSLFTextShape, возьмите абзацы и обработайте их, как вы.Если вы получаете XSLFGroupShape, повторите и их getShapes().Поскольку они могут содержать разные типы фигур, вы можете использовать для этого рекурсию.Вы также можете обращаться с типом фигуры XSLFTable.

Но настоящая проблема начинается тогда, когда вы понимаете, что то, что вы хотите заменить, разделено на несколько прогонов; -)

0 голосов
/ 24 сентября 2018

Если нужно просто получить все текстовое содержимое независимо от того, в каких объектах оно находится, тогда можно просто сделать именно это.Текстовое содержимое содержится в org.apache.xmlbeans.XmlString элементах.В PowerPoint XML они находятся в a:t тегах.Пространство имен a = "http://schemas.openxmlformats.org/drawingml/2006/main".

Таким образом, следующий код получает весь текст во всех объектах на всех слайдах и заменяет строку" test "без учета регистра на" XXXXXXXX ".

import java.io.FileInputStream;
import java.io.FileOutputStream;

import org.apache.poi.xslf.usermodel.*;
import org.openxmlformats.schemas.presentationml.x2006.main.CTSlide;

import org.apache.xmlbeans.XmlObject;
import org.apache.xmlbeans.XmlString;

public class ReadPPTXAllText {

 public static void main(String[] args) throws Exception {

  XMLSlideShow slideShow = new XMLSlideShow(new FileInputStream("MicrosoftPowerPoint.pptx"));
  for (XSLFSlide slide : slideShow.getSlides()) {
   CTSlide ctSlide = slide.getXmlObject();
   XmlObject[] allText = ctSlide.selectPath(
    "declare namespace a='http://schemas.openxmlformats.org/drawingml/2006/main' " +
    ".//a:t"
   );
   for (int i = 0; i < allText.length; i++) {
    if (allText[i] instanceof XmlString) {
     XmlString xmlString = (XmlString)allText[i];
     String text = xmlString.getStringValue();
System.out.println(text);
     if (text.toLowerCase().contains("test")) {
      String newText = text.replaceAll("(?i)" + "test", "XXXXXXXX");
      xmlString.setStringValue(newText);
     }
    }
   }
  }

  FileOutputStream out = new FileOutputStream("MicrosoftPowerPointChanged.pptx");
  slideShow.write(out);
  slideShow.close();
  out.close();
 }
}
...