Sofi
Sofi

Reputation: 1

How to create section, subsection and subsubsection in a Word file using Apache POI?

I read Word document in Java using Apache POI, but I can’t find any references to create section, subsection ect. in a Word file. Also, I’m trying to create table of contents with number of this added sections. I pasted a part of my code to show you what I’ve done:

   public static void main(String[] args) throws FileNotFoundException, IOException {

        File out = new File("POIExamlpe.docx");

        XWPFDocument document = new XWPFDocument();
        XWPFStyles styles = document.createStyles();

        XWPFWordExtractor we = new XWPFWordExtractor(document);
        System.out.println(we.getText());

        //Create multilevel  list in word with different styles, form the next level
        CreateParagraph(document, styles, "First Level@@Second Level@@First Level@@Second Level@@Three Level@@Second Level@@Three Level@@Second Level@@First Level");

        document.createTOC();
}   
public static void CreateParagraph(XWPFDocument doc, XWPFStyles style,String content ){
    for (String value : content.split("@@")) {
        XWPFParagraph para = doc.createParagraph();
        para.setVerticalAlignment(TextAlignment.CENTER);
        para.setNumID(BigInteger.valueOf(1));
        para.setStyle(heading1);
        if (value.contains("Second")) {   para.getCTP().getPPr().getNumPr().addNewIlvl().setVal(BigInteger.valueOf(1));
            para.setStyle(heading2);
        }
        if(value.contains("Three")){     para.getCTP().getPPr().getNumPr().addNewIlvl().setVal(BigInteger.valueOf(2));
            para.setStyle(heading4);
        }
        XWPFRun run = para.createRun(); 

}

I generated this document

But I want to generate something like this.

Upvotes: 0

Views: 966

Answers (1)

Axel Richter
Axel Richter

Reputation: 61945

Whether this works or not depends on your POIExamlpe.docx. This must contain numbering definitions within a \word\numberings.xml. For example:

<w:abstractNum w:abstractNumId="0">
 <w:multiLevelType w:val="multilevel"/>
 <w:lvl w:ilvl="0">
  <w:start w:val="1"/>
  <w:numFmt w:val="decimal"/>
  <w:pStyle w:val="Heading1"/>
  <w:lvlText w:val="%1"/>
  <w:lvlJc w:val="left"/>
  <w:pPr>
   <w:ind w:hanging="432" w:left="432"/>
  </w:pPr>
 </w:lvl>

 <w:lvl w:ilvl="1">
  <w:start w:val="1"/>
  <w:numFmt w:val="decimal"/>
  <w:pStyle w:val="Heading2"/>
  <w:lvlText w:val="%1.%2"/>
  <w:lvlJc w:val="left"/>
  <w:pPr>
   <w:ind w:hanging="576" w:left="576"/>
  </w:pPr>
 </w:lvl>

 <w:lvl w:ilvl="2">
  <w:start w:val="1"/>
  <w:numFmt w:val="decimal"/>
  <w:pStyle w:val="Heading3"/>
  <w:lvlText w:val="%1.%2.%3"/>
  <w:lvlJc w:val="left"/>
  <w:pPr>
   <w:ind w:hanging="720" w:left="720"/>
  </w:pPr>
 </w:lvl>

</w:abstractNum>

<w:num w:numId="1">
 <w:abstractNumId w:val="0"/>
</w:num>

Your code line

para.setNumID(BigInteger.valueOf(1));

refers to the numID1 which refers to the abstractNumId 0 which defines the numbering.

Your code line

para.getCTP().getPPr().getNumPr().addNewIlvl().setVal(BigInteger.valueOf(1));

refers to the ilvl 1 which defines the style of the numbering level. For example in this level <w:lvlText w:val="%1.%2"/>.

How can you check this? A *.docx file is simply a ZIP archive containing XML files and other files within a special directory structure. So you can unzip this *.docx file and have a look in it.

To create an appropriate template, create a new Word document, use all needed headings in it and number them. Save the file as POIExamlpe.docx. Now you can delete the content and saving again. Now unzip this *.docx file and have a look at \word\numberings.xml.

Upvotes: 1

Related Questions