2017-01-19 1 views
-2

iText5에서 우리는 "public float calculateHeights (boolean firsttime)"이 필요할 때 PdfPTable의 높이를 얻을 수 있습니다.iText7에서 iText5의 calculateHeights 메소드와 같은 방법이 있습니까?

iText7에서 (현재 상위 요소에 테이블을 추가하기 전에) 현재 테이블 높이 값을 얻는 방법은 무엇입니까?

이미 "table.getHeight()"메소드를 테스트했지만 null을 반환합니다. 그리고 테이블 렌더링 객체에서이 값을 얻을 수 있지만 제한 사항은 테이블이 부모 요소에 추가 될 때 렌더링이 트리거되어야하므로 시간이 필요 없다는 점입니다.

때때로 "y 축"값을 결정할 때이 값을 계산에 사용해야합니다.

+0

당신은 높이가 너비를 알 수없는 경우 계산 될 수 없다는 인식을 document.setFontSize(24);를 시청, 당신은? 폭이 좁은 테이블은 넓은 테이블보다 더 높은 높이가 필요합니다. 폭을 설정했다는 것을 증명하는 코드를 보여줄 수 있습니까? –

+0

안녕하세요, Brian, 답장을 보내 주시면 대단히 기쁩니다. – Schoner

+0

나는 당신의 의미를 안다. 그러나 iText5에서 우리는 이것에 대해 걱정할 필요가 없다. 그냥 메서드를 호출하면된다. 다음은 간단한 예제입니다. alused는 테이블의 너비를 설정하고 하나의 문자열 만 추가하지만 여전히 높이 값을 가져올 수 없습니다. 테이블 테이블 = 새 테이블 (1); table.setWidth (300); table.addCell ("1"); // 결과 : 높이 = null System.out.println ("height ="+ table.getHeight()); – Schoner

답변

2

는 자신의 위치/크기에 대한 요소 및 정보는 당신이 PdfPTable 요소에 calculateWidths를 호출 할 수있는, 약간 혼합했다.

iText7에서이 기능은 분리되어있어 렌더링/레이아웃 요소에 다양한 종류의 유연성을 부여합니다.

따라서 모델 요소는 Table 인스턴스의 예이며, 위치 나 크기에 대해서는 알지 못합니다. 그리고 table.getHeight을 호출하면 에 이전에 HEIGHT 속성이 설정되어 있지 않으므로 null이됩니다.

테이블 높이를 계산하려면 렌더링 기능을 사용해야합니다.

모델 요소의 경우이 모델 요소와 모든 자식을 나타내는 렌더러의 하위 트리를 가져올 수 있으며 주어진 영역에 layout을 가져올 수 있습니다. 테이블의 높이를 실제로 알기 위해서는 엘리먼트의 전체 내용을 배치하기에 충분할만큼 의도적으로 충분한 영역을 생성하기를 원할 것입니다. 내게 인쇄 22.982422O 상기

PdfDocument pdfDoc = ... 
Document doc = ... 

Table table = new Table(2) 
      .addCell(new Cell().add(new Paragraph("cell 1, 1"))) 
      .addCell(new Cell().add(new Paragraph("cell 1, 2"))); 
LayoutResult result = table.createRendererSubTree().setParent(doc.getRenderer()).layout(
      new LayoutContext(new LayoutArea(1, new Rectangle(0, 0, 400, 1e4f)))); 

System.out.println(result.getOccupiedArea().getBBox().getHeight()); 

코드 있지만 결과 및 구성 요소의 특성에 따라 달라질 수있다.

내가 코드의 두 가지 중요한 부분을 지적하고 싶으면는 :

  1. 우리는이 전체 테이블을 배치하기에 충분 것을 고려하여 LayoutArea의 높이로 1e4f를 전달합니다. 테이블을 그 높이에 놓을 수 없다면, 결과는이 주어진 높이를 초과 할 수 없으므로, 당신의 유스 케이스 (테이블의 전체 높이를 아십시오)에 맞지 않을 것입니다. 따라서 전체 테이블을 배치하기에 충분한 높이를 전달하십시오.

  2. .setParent(doc.getRenderer()) 부분은 여기에서 중요하며 상속 속성을 검색하는 데 사용됩니다. table 요소, 심지어 글꼴로 많은 속성을 설정하지 않았지만이 정보는이 요소가 차지할 영역을 아는 데 필수적입니다. 따라서이 정보는 layout 동안 상위 체인에서 상속됩니다. document.setFont(newFont);, 또는 글꼴 크기 : 문서의 글꼴을 변경하여 테스트 할 수 있습니다 결과 높이 변화

+0

많은 감사, Alexey ... – Schoner

1

글쎄, 렌더러 프레임 워크가 iText7에서 작성된 방식으로 인해 레이아웃 객체의 높이를 부모 문서에 추가하기 전에 높이를 계산할 방법이 없습니다. 레이아웃 객체의 높이는 Document 객체에 추가 될 때 발생합니다.

그러나 이전에 추가 한 요소의 내용을 변경할 수 있도록 Document을 다시 레이아웃 할 수 있습니다. 이것을 사용하여 테이블 렌더링을 시뮬레이션하고 새 요소를 추가 할 때 테이블 높이를 유지할 수 있습니다. table.getHeight()은 height 속성을 검색하고 그 속성이 현재 테이블 렌더링 프로세스의 아무 곳에서나 설정되지 않기 때문에 여전히 작동하지 않습니다.

아래 예에서는 렌더러 트리를 반복하고 문서에서 각 테이블이 차지하는 영역을 인쇄하여 계산 된 높이를 얻는 방법을 보여주는 편리한 방법을 작성했습니다.

예제 자체는 문서에 테이블을 추가하고, 점유 된 영역을 표시하고, 각 테이블에 셀을 추가하고, 점유 된 영역을 표시합니다 (이전에 추가 된 요소에 추가하면 트리거되지 않습니다 레이아웃), 마지막으로 수동으로 다시 레이아웃을 트리거하고 최종 점유 영역을 표시합니다. iText5에서

public class DelayedLayout { 
    public static String DEST = "target/output/StackOverflow/DelayedLayout/delayed.pdf"; 

    public static void main(String[] args)throws IOException, FileNotFoundException{ 
     File file = new File(DEST); 
     file.getParentFile().mkdirs(); 
     new DelayedLayout().createPdf(DEST); 
    } 

    public void createPdf(String dest) throws IOException, FileNotFoundException{ 
     PdfWriter writer = new PdfWriter(dest); 
     PdfDocument pdfDoc = new PdfDocument(writer); 
     boolean immediateFlush = false; 
     boolean relayout = true; 
     //Set immediate layout to false, so the document doesn't immediatly write render-results to its outputstream 
     Document doc = new Document(pdfDoc, PageSize.A4,immediateFlush); 
     Table tOne = createSimpleTable(); 
     for(int i= 0; i< 5; i++) { 
      //Add a table and some whitespace 
      doc.add(tOne); 

      doc.add(new Paragraph("")); 

     } 
     System.out.println("\nInitial layout results"); 
     printOccupiedAreasOfTableRenderers(doc.getRenderer()); 
     System.out.println("\nAdding extra cells to the table"); 
     addToTable(tOne); 
     printOccupiedAreasOfTableRenderers(doc.getRenderer()); 
     System.out.println("\nForcing the document to redo the layout"); 
     if(relayout)doc.relayout(); 
     printOccupiedAreasOfTableRenderers(doc.getRenderer()); 
     doc.close(); 
    } 

    /** 
    * Create a very simple table 
    * @return simple table 
    */ 
    private Table createSimpleTable(){ 
     int nrOfCols = 3; 
     int nrOfRows = 5; 

     Table res = new Table(nrOfCols); 
     for(int i= 0; i<nrOfRows;i++){ 
      for(int j = 0; j<nrOfCols;j++){ 
       Cell c = new Cell(); 
       c.add(new Paragraph("["+i+", "+j+"]")); 
       res.addCell(c); 
      } 
     } 

     return res; 
    } 

    /** 
    * Add some extra cells to an exisiting table 
    * @param tab table to add cells to 
    */ 
    private void addToTable(Table tab){ 
     int nrOfRows = 5; 
     int nrOfCols = tab.getNumberOfColumns(); 
     for(int i=0; i<nrOfRows*nrOfCols;i++){ 
      Cell c = new Cell(); 
      c.add(new Paragraph("Extra cell"+ i)); 
      tab.addCell(c); 
     } 

    } 

    /** 
    * Recursively iterate over the renderer tree, writing the occupied area to the console 
    * @param currentNode current renderer-node to check 
    */ 
    private void printOccupiedAreasOfTableRenderers(IRenderer currentNode){ 
     if(currentNode.getClass().equals(TableRenderer.class)){ 
      System.out.println("Table renderer with occupied area: " + currentNode.getOccupiedArea()); 
     } 
     for (IRenderer child:currentNode.getChildRenderers()) { 
      printOccupiedAreasOfTableRenderers(child); 
     } 
    } 
+0

많은 감사, 사무엘 ... – Schoner

관련 문제