Home > database >  Why STOnOff Enums are removed in Apache 5.2.2 ? How to set X_0 & X_1 values?
Why STOnOff Enums are removed in Apache 5.2.2 ? How to set X_0 & X_1 values?

Time:05-03

I was using STOnOff.X_0 Enum to set value as 0(i.e false) for some elements in Apache POI 3.14 when constructing docx file. But now currently in latest version 5.2.2, I could this class has been changed & also new class named as STOnOff1 is being introduced with On & Off enums. Based on below stackoverflow thread I could see that it is suggested to use true or false.

Similar Stackoverflow thread

Why is STOnOff class removed & an another class like STOnOff1 is introduced without having STOnOff1.X_0 & STOnOff1.X_1 enums but just STOnOff1.OFF & STOnOff1.ON ? Can I use STTrueFalse.True/STTrueFalse.False in place of just boolean true/false ? Any detailed clarification/solution reg these changes will be really helpful.

Concrete Examples:

1)For setEqualWidth(STOnOff value) of Section's column Layout, we could see that previously in POI 3.14 we need to set STOnOff value as STOnOff.X_1, etc.. But in Apache POI 5.2.2 it is now accepting any Object value, so can we set STTrueFalse.True/boolean true (or) false instead of STOnOff.X_1 in setEqualWidth() API now ?

Also could see that any CT API's like setEqualWidth(STOnOff value) which previously accepted STOnOff.Enum values had now changed to accept Object param for which can we pass STTrueFalse.True/STTrueFalse.False instead of plain boolean true(or) false ?

import java.math.BigDecimal;
import java.math.BigInteger;
import java.util.List;

import org.apache.poi.xwpf.usermodel.XWPFDocument;
import org.openxmlformats.schemas.officeDocument.x2006.sharedTypes.STOnOff;
import org.openxmlformats.schemas.officeDocument.x2006.sharedTypes.STTrueFalse;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTPageMar;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTSectPr;

public class STOnOffValuesTesting {

    public static void main(String[] args) {
        
        try {
        byte[] docbytes = FileUtil.read("anysimpleDocxFile.docx"); //No i18n
        InputStream documentStream = GeneralUtils.getStreamFromArray( docbytes );
        XWPFDocument document = new XWPFDocument( documentStream );
        List<CTSectPr> documentSections = document.docSections;
        int length = documentSections.size();

        for(int i=0; i <length; i  ){
            CTSectPr sectPr = documentSections.get(i);

            //In Apache POI 3.14
            sectPr.getCols().setEqualWidth(STOnOff.X_1);
            

            //But in Apache POI 5.2.2
            sectPr.getCols().setEqualWidth(true);
            sectPr.getCols().setEqualWidth(STTrueFalse.TRUE); //Is this correct ?
            }
        }catch(Exception e) {
            System.out.println(e)
        }
    }
}```

CodePudding user response:

When using the low level Office Open XML-schemas classes, a programmer needs to know in detail what those classes are doing. That's the aim of apache poi: To provide a high level layer to use those low level classes.

Where are the Office Open XML-schemas classes coming from?

Those classes are generated form XSD files which are published in ECMA-376. They are contained in download part 4. The XSDs contain definitions for the XML which gets used in Office Open XML. XMLBeans from Apache provides methods to auto-generate Java classes from this XSDs. So the low-level low level Office Open XML-schemas classes of ooxml-schemas or poi-ooxml-lite or poi-ooxml-full do fully translate the given XSD definitions to Java.

So the general answer to your question about the reason of changes in this Office Open XML-schemas classes is that the published XSDs have changed from 1st edition in 2006 up to 4th edition in 2012. Or the used XMLBeans version has changed and does the XSD - Java - translation a little bit different.

STOnOff versus STTrueFalse

The XML type ST_OnOff was defined in 1st edition of wml.xsd as an enumeration of "true", "false", "on", "off", "1", "0". Now in 4th edition it is defined in shared-commonSimpleTypes.xsd as xsd:boolean and ST_OnOff1, where ST_OnOff1 is an enumeration of "on", "off". This is probably done because xsd:boolean contains "true", "false", "1", "0" already. So it can replace the former used enumeration.

The The XML type ST_TrueFalse was defined in 1th edition of vml-main.xsd as an enumeration of "t", "f", "true", "false". Now in 4th edition it is defined in shared-commonSimpleTypes.xsd also as an enumeration of "t", "f", "true", "false". But it only gets used in VML.

So STTrueFalse and STOnOff are not the same. The one cannot be used in place of the other. Whether the one or the other needs to be used is determined by the context. It is defined by XML types which use either the ST_TrueFalse or the ST_OnOff type. For example the type CT_OnOff in wordprocessing which uses ST_OnOff or multiple VML types which use ST_TrueFalse.

In terms of Java and CTSectPr - CTColumns.setEqualWidth one can simply test this using following code using apache poi 5.2.2:

import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTSectPr;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTColumns;
import org.openxmlformats.schemas.officeDocument.x2006.sharedTypes.STTrueFalse;
import org.openxmlformats.schemas.officeDocument.x2006.sharedTypes.STOnOff1;

class STOnOffValuesTesting {

 public static void main(String[] args) throws Exception {
  CTSectPr sectPr = CTSectPr.Factory.newInstance();
  CTColumns cols = sectPr.addNewCols();
  cols.setEqualWidth(true); //cols.setEqualWidth(false); // works and gets used by Apache POI by default
  System.out.println(sectPr);
  cols.setEqualWidth("1"); //cols.setEqualWidth("0"); // works and gets used by Microsoft by default
  System.out.println(sectPr);
  cols.setEqualWidth(STOnOff1.ON); //cols.setEqualWidth(STOnOff1.OFF); // works but never gets used by Microsoft instead of boolean 
  System.out.println(sectPr);
  //cols.setEqualWidth(STTrueFalse.TRUE); //cols.setEqualWidth(STTrueFalse.FALSE); // will not work as STTrueFalse only gets used in VML
 }
}

The cols.setEqualWidth(STTrueFalse.TRUE) throws an exception. The cols.setEqualWidth(STOnOff1.ON) works per definition. But I would not use this because Microsoft Word itself never uses "on"/"off" in this context.

  • Related