0

I am creating an .xls excel file using apache poi. I need to set the Page Breaks View by default. But I did look at a related question on .xlsx file . I didn't find anything "how to set Page Breaks View Mode" to using HSSF of ApachePOI

enter image description here

  • 1
    have you tried google? statckoverflow have many answers related to this question https://stackoverflow.com/questions/28539760/apache-poi-page-breaks – Popeye Dec 16 '21 at 03:36
  • 1
    Do you mean print areas? You can get or set the print areas using HSSFPrintSetup as shown here: https://poi.apache.org/apidocs/dev/org/apache/poi/hssf/usermodel/HSSFPrintSetup.html for example `PrintSetup ps = sheet.getPrintSetup(); ps.setFitHeight(pageCount);` – sorifiend Dec 16 '21 at 03:37
  • I don't know exactly what you are asking, but this may be helpful: https://stackoverflow.com/questions/7861001/set-page-view-mode-in-excel-file-using-apache-poi – sorifiend Dec 16 '21 at 03:41
  • I try stackoverflow.com/questions/7861001/… but It didn't work. – Huy Nguyen Dec 16 '21 at 03:49
  • @sorifiend i think it don't print areas. It is View modes for Excel. Please see my attachment – Huy Nguyen Dec 16 '21 at 03:56
  • Ok, so CTSheetView is actually part of the openxmlformats library, with the following import `import org.openxmlformats.schemas.spreadsheetml.x2006.main.*;` and does not appear to be exposed from within Apache POI, however, once you have added this library you should then be able to interact with CTSheetView similar to how it is done within Apache POI: https://github.com/apache/poi/blob/a60f552c5908dfaad31cfc0db6ef82690dcd5b96/poi-ooxml/src/main/java/org/apache/poi/xssf/usermodel/XSSFSheet.java#L3503 I will leave the rest with you, that is enough digging for me. – sorifiend Dec 16 '21 at 04:23

1 Answers1

1

The binary BIFF file system of *.xls and the Office Open XML file system of *.xlsx are two totally different file systems. You can't mix them. In apache poi HSSF ist for the one and XSSF for the other. The high level classes of apache poi try providing methods for both the file systems. This gets done using interfaces in SS. But outside the high level classes one needs strictly differentiate the both file systems.

Setting page break preview for a sheet is not provided by the high level classes up to now. So we need the underlyinf low lewel classes. For XSSF this are the org.openxmlformats.schemas.spreadsheetml.x2006.main.* classes, which are the XML representation of the XSSF internals. But for HSSF this are the org.apache.poi.hssf.record.* classes, which are the binary representation of the HSSF internals.

Setting page break preview for a sheet could be done like so for both the file systems:

import java.io.*;

import org.apache.poi.ss.usermodel.*;
import org.apache.poi.xssf.usermodel.*;
import org.apache.poi.hssf.usermodel.*;

import org.apache.poi.hssf.model.InternalSheet;
import org.apache.poi.hssf.record.WindowTwoRecord;

public class ExcelPageBreakPreview {
  
 public static void main(String[] args) throws Exception {
  //Workbook workbook = WorkbookFactory.create(new FileInputStream("./ExcelTemplate.xlsx")); String filePath = "./ExcelInPageBreakPreview.xlsx";
  Workbook workbook = WorkbookFactory.create(new FileInputStream("./ExcelTemplate.xls")); String filePath = "./ExcelInPageBreakPreview.xls";

  Sheet sheet = workbook.getSheetAt(0);

  //set sheet in PageBreakPreview
  if (sheet instanceof XSSFSheet) {
   XSSFSheet xssfSheet= (XSSFSheet)sheet;   
   xssfSheet.lockSelectLockedCells(true);
   xssfSheet.getCTWorksheet().getSheetViews().getSheetViewArray(0).setView(org.openxmlformats.schemas.spreadsheetml.x2006.main.STSheetViewType.PAGE_BREAK_PREVIEW);   
  } else if (sheet instanceof HSSFSheet) {
   HSSFSheet hssfSheet= (HSSFSheet)sheet; 
   InternalSheet internalSheet = hssfSheet.getSheet(); 
   WindowTwoRecord record = internalSheet.getWindowTwo();
   record.setSavedInPageBreakPreview(true);
  }

  FileOutputStream fileOut = new FileOutputStream(filePath);
  workbook.write(fileOut);
  fileOut.close();
  workbook.close();
 }
}

Previous apache poi versions might not have InternalSheet HSSFSheet.getSheet public. Then one needs using reflection to get the InternalSheet:

   //InternalSheet internalSheet = hssfSheet.getSheet(); 
   java.lang.reflect.Field _sheet = HSSFSheet.class.getDeclaredField("_sheet");
   _sheet.setAccessible(true); 
   InternalSheet internalSheet = (InternalSheet)_sheet.get(hssfSheet); 
Axel Richter
  • 56,077
  • 6
  • 60
  • 87
  • Thank you, I will try it – Huy Nguyen Dec 16 '21 at 14:12
  • when i checked HSSFSheet.class then method getSheet() is lock in package . I'm using Apache POI version 3.17. Is there any other way? – Huy Nguyen Dec 17 '21 at 09:51
  • @Huy Nguyễn Ngọc: My examples always using the current `apache poi` version. Simply do not using ancient versions. They are not more supported by `apache poi`. In `apache poi 3.17` one needs using reflection to get the `InternalSheet`. See my supplement in the answer. – Axel Richter Dec 17 '21 at 10:44
  • thank, It's working for me – Huy Nguyen Dec 18 '21 at 09:13