Save This Page
Home » iText-src-2.1.3 » com.lowagie » text » pdf » [javadoc | source]
    1   /*
    2    * $Id: PdfPages.java 3373 2008-05-12 16:21:24Z xlv $
    3    *
    4    * Copyright 1999, 2000, 2001, 2002 Bruno Lowagie
    5    *
    6    * The contents of this file are subject to the Mozilla Public License Version 1.1
    7    * (the "License"); you may not use this file except in compliance with the License.
    8    * You may obtain a copy of the License at http://www.mozilla.org/MPL/
    9    *
   10    * Software distributed under the License is distributed on an "AS IS" basis,
   11    * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
   12    * for the specific language governing rights and limitations under the License.
   13    *
   14    * The Original Code is 'iText, a free JAVA-PDF library'.
   15    *
   16    * The Initial Developer of the Original Code is Bruno Lowagie. Portions created by
   17    * the Initial Developer are Copyright (C) 1999, 2000, 2001, 2002 by Bruno Lowagie.
   18    * All Rights Reserved.
   19    * Co-Developer of the code is Paulo Soares. Portions created by the Co-Developer
   20    * are Copyright (C) 2000, 2001, 2002 by Paulo Soares. All Rights Reserved.
   21    *
   22    * Contributor(s): all the names of the contributors are added in the source code
   23    * where applicable.
   24    *
   25    * Alternatively, the contents of this file may be used under the terms of the
   26    * LGPL license (the "GNU LIBRARY GENERAL PUBLIC LICENSE"), in which case the
   27    * provisions of LGPL are applicable instead of those above.  If you wish to
   28    * allow use of your version of this file only under the terms of the LGPL
   29    * License and not to allow others to use your version of this file under
   30    * the MPL, indicate your decision by deleting the provisions above and
   31    * replace them with the notice and other provisions required by the LGPL.
   32    * If you do not delete the provisions above, a recipient may use your version
   33    * of this file under either the MPL or the GNU LIBRARY GENERAL PUBLIC LICENSE.
   34    *
   35    * This library is free software; you can redistribute it and/or modify it
   36    * under the terms of the MPL as stated above or under the terms of the GNU
   37    * Library General Public License as published by the Free Software Foundation;
   38    * either version 2 of the License, or any later version.
   39    *
   40    * This library is distributed in the hope that it will be useful, but WITHOUT
   41    * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
   42    * FOR A PARTICULAR PURPOSE. See the GNU Library general Public License for more
   43    * details.
   44    *
   45    * If you didn't download this code from the following link, you should check if
   46    * you aren't using an obsolete version:
   47    * http://www.lowagie.com/iText/
   48    */
   49   
   50   package com.lowagie.text.pdf;
   51   
   52   import java.io.IOException;
   53   import java.util.ArrayList;
   54   
   55   import com.lowagie.text.DocumentException;
   56   import com.lowagie.text.ExceptionConverter;
   57   
   58   /**
   59    * <CODE>PdfPages</CODE> is the PDF Pages-object.
   60    * <P>
   61    * The Pages of a document are accessible through a tree of nodes known as the Pages tree.
   62    * This tree defines the ordering of the pages in the document.<BR>
   63    * This object is described in the 'Portable Document Format Reference Manual version 1.3'
   64    * section 6.3 (page 71-73)
   65    *
   66    * @see		PdfPage
   67    */
   68   
   69   public class PdfPages {
   70       
   71       private ArrayList pages = new ArrayList();
   72       private ArrayList parents = new ArrayList();
   73       private int leafSize = 10;
   74       private PdfWriter writer;
   75       private PdfIndirectReference topParent;
   76       
   77       // constructors
   78       
   79   /**
   80    * Constructs a <CODE>PdfPages</CODE>-object.
   81    */
   82       
   83       PdfPages(PdfWriter writer) {
   84           this.writer = writer;
   85       }
   86       
   87       void addPage(PdfDictionary page) {
   88           try {
   89               if ((pages.size() % leafSize) == 0)
   90                   parents.add(writer.getPdfIndirectReference());
   91               PdfIndirectReference parent = (PdfIndirectReference)parents.get(parents.size() - 1);
   92               page.put(PdfName.PARENT, parent);
   93               PdfIndirectReference current = writer.getCurrentPage();
   94               writer.addToBody(page, current);
   95               pages.add(current);
   96           }
   97           catch (Exception e) {
   98               throw new ExceptionConverter(e);
   99           }
  100       }
  101       
  102       PdfIndirectReference addPageRef(PdfIndirectReference pageRef) {
  103           try {
  104               if ((pages.size() % leafSize) == 0)
  105                   parents.add(writer.getPdfIndirectReference());
  106               pages.add(pageRef);
  107               return (PdfIndirectReference)parents.get(parents.size() - 1);
  108           }
  109           catch (Exception e) {
  110               throw new ExceptionConverter(e);
  111           }
  112       }
  113       
  114       // returns the top parent to include in the catalog
  115       PdfIndirectReference writePageTree() throws IOException {
  116           if (pages.isEmpty())
  117               throw new IOException("The document has no pages.");
  118           int leaf = 1;
  119           ArrayList tParents = parents;
  120           ArrayList tPages = pages;
  121           ArrayList nextParents = new ArrayList();
  122           while (true) {
  123               leaf *= leafSize;
  124               int stdCount = leafSize;
  125               int rightCount = tPages.size() % leafSize;
  126               if (rightCount == 0)
  127                   rightCount = leafSize;
  128               for (int p = 0; p < tParents.size(); ++p) {
  129                   int count;
  130                   int thisLeaf = leaf;
  131                   if (p == tParents.size() - 1) {
  132                       count = rightCount;
  133                       thisLeaf = pages.size() % leaf;
  134                       if (thisLeaf == 0)
  135                           thisLeaf = leaf;
  136                   }
  137                   else
  138                       count = stdCount;
  139                   PdfDictionary top = new PdfDictionary(PdfName.PAGES);
  140                   top.put(PdfName.COUNT, new PdfNumber(thisLeaf));
  141                   PdfArray kids = new PdfArray();
  142                   ArrayList internal = kids.getArrayList();
  143                   internal.addAll(tPages.subList(p * stdCount, p * stdCount + count));
  144                   top.put(PdfName.KIDS, kids);
  145                   if (tParents.size() > 1) {
  146                       if ((p % leafSize) == 0)
  147                           nextParents.add(writer.getPdfIndirectReference());
  148                       top.put(PdfName.PARENT, (PdfIndirectReference)nextParents.get(p / leafSize));
  149                   }
  150                   writer.addToBody(top, (PdfIndirectReference)tParents.get(p));
  151               }
  152               if (tParents.size() == 1) {
  153                   topParent = (PdfIndirectReference)tParents.get(0);
  154                   return topParent;
  155               }
  156               tPages = tParents;
  157               tParents = nextParents;
  158               nextParents = new ArrayList();
  159           }
  160       }
  161       
  162       PdfIndirectReference getTopParent() {
  163           return topParent;
  164       }
  165       
  166       void setLinearMode(PdfIndirectReference topParent) {
  167           if (parents.size() > 1)
  168               throw new RuntimeException("Linear page mode can only be called with a single parent.");
  169           if (topParent != null) {
  170               this.topParent = topParent;
  171               parents.clear();
  172               parents.add(topParent);
  173           }
  174           leafSize = 10000000;
  175       }
  176   
  177       void addPage(PdfIndirectReference page) {
  178           pages.add(page);
  179       }
  180   
  181       int reorderPages(int order[]) throws DocumentException {
  182           if (order == null)
  183               return pages.size();
  184           if (parents.size() > 1)
  185               throw new DocumentException("Page reordering requires a single parent in the page tree. Call PdfWriter.setLinearMode() after open.");
  186           if (order.length != pages.size())
  187               throw new DocumentException("Page reordering requires an array with the same size as the number of pages.");
  188           int max = pages.size();
  189           boolean temp[] = new boolean[max];
  190           for (int k = 0; k < max; ++k) {
  191               int p = order[k];
  192               if (p < 1 || p > max)
  193                   throw new DocumentException("Page reordering requires pages between 1 and " + max + ". Found " + p + ".");
  194               if (temp[p - 1])
  195                   throw new DocumentException("Page reordering requires no page repetition. Page " + p + " is repeated.");
  196               temp[p - 1] = true;
  197           }
  198           Object copy[] = pages.toArray();
  199           for (int k = 0; k < max; ++k) {
  200               pages.set(k, copy[order[k] - 1]);
  201           }
  202           return max;
  203       }
  204   }

Save This Page
Home » iText-src-2.1.3 » com.lowagie » text » pdf » [javadoc | source]