001/* 002 * CombineTwoPDF 003 * A simple tool to combine two PDF document's into one larger size pdf 004 * containing both on the same page. It is usefull when you have a scan of a 005 * large doc that could not be scanned into one page. This will take two 006 * seperate files and produce one file that has a page size twice the size of 007 * the first docs page size with the original doc merged into the final double 008 * size pdf doc. 009 * 010 * $URL: svn://svn.webarts.bc.ca/open/trunk/projects/WebARTS/ca/bc/webarts/tools/pdf/CombineTwoPDF.java $ 011 * $REVISION: $ 012 * Copyright (C) 2003 Tom Gutwin 013 * tgutwin@webarts.bc.ca 014 * 015 * 016 * This program is free software; you can redistribute it and/or 017 * modify it under the terms of the GNU General Public License 018 * as published by the Free Software Foundation; either version 2 019 * of the License, or any later version. 020 * 021 * This program is distributed in the hope that it will be useful, 022 * but WITHOUT ANY WARRANTY; without even the implied warranty of 023 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 024 * GNU General Public License for more details. 025 * 026 * You should have received a copy of the GNU General Public License 027 * along with the jEdit program; if not, write to the Free Software 028 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. 029 */ 030 031package ca.bc.webarts.tools.pdf; 032 033import ca.bc.webarts.tools.NativeAppLauncher; 034 035import com.itextpdf.text.*; 036import com.itextpdf.text.pdf.*; 037 038import java.io.*; 039 040 041/** 042 * A Utility class to combine two PDF document's into one larger size pdf 043 * containing both on the same page. It is usefull when you have a scan of a 044 * large doc that could not be scanned into one page. This will take two 045 * seperate files and produce one file that has a page size twice the size of 046 * the first docs page size with the original doc merged into the final double 047 * size pdf doc.<br> 048 * <br> 049 * Examples:<br> 050 * java ca.bc.webarts.tools.CombineTwoPDF resultFilename file1.pdf file2.pdf<br> 051 * <p><b>It does it all in Java (no native code calls) and its FREE!</b></p> 052 * <br>All PDF document handling is done using the freely available iText PDF 053 * Java library - 054 * <a href="http://www.lowagie.com/iText/">http://www.lowagie.com/iText/</a> 055 * <hr><br>License: GNU GPL<pre> 056 * This program is free software; you can redistribute it and/or modify it 057 * under the terms of the GNU General Public License as published by the Free 058 * Software Foundation; version 2 of the License. 059 * 060 * This program is distributed in the hope that it will be useful, but WITHOUT 061 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 062 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for 063 * more details. 064 * 065 * You should have received a copy of the GNU General Public License along 066 * with this program; if not, write to the Free Software Foundation, Inc., 067 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.</pre> 068 * 069 * @author TGutwin 070 */ 071public class CombineTwoPDF 072{ 073 074 /** Description of the Field */ 075 private static String outFileName_ = "combinedOut.pdf"; 076 077 /** Description of the Field */ 078 private static String inFileName_ = "infile.pdf"; 079 private static String inFileName2_ = "infile2.pdf"; 080 081 /** Description of the Field */ 082 private static float cropBorder_ = 0.0f; 083 084 /** Description of the Field */ 085 private static Rectangle outputPageSize_ = PageSize.LETTER;//PageSize.A4; 086 087 /** The amount to scale a page so it will fit 2Up on the page. 088 The Inital/default scale is based on a 8.5X11 page.**/ 089 private static float scale_ = (outputPageSize_.getHeight() / 2.0f) / (outputPageSize_.getWidth() - (2.0f * cropBorder_)); 090 091 /** The offset amount to get it placed from the origin of the page.*/ 092 private static int vertOffset_ = ((new Float(62.0f * cropBorder_)).intValue()); 093 private static int horizOffset_ = ((new Float(62.0f * cropBorder_)).intValue()); 094 095 /** Description of the Field */ 096 private static double rotation_ = Math.toRadians(0); 097 098 /** Flags if acroreader is auto launched after this process. */ 099 private static boolean launchAcroread_ = true; 100 101 /** Flag for double sided printing binding offset on the long side of the page */ 102 private static boolean bindingOffset_ = false; 103 /** 104 * The amount to offset the long side of the page if a double sided print 105 * page offset is requested. (default is 0.75 inches) 106 **/ 107 private static float topOffsetAmount_ = ((new Float(62.0f * 0.0f)).intValue()); 108 private static String acroCmd_ = "C:\\Progra~1\\Adobe\\Acroba~1.0\\Reader\\AcroRD32.exe"; 109 /** Description of the Field */ 110 private static String usage_ ="SYNTAX: CombineTwoPDF resultFilename file1.pdf"+ 111 " file2.pdf [horizoffset vertoffset]\nThe "+ 112 "offsets apply to the placement of the 2ndpage only"; 113 114 115 /** 116 * The main program for the class.<br>It should be called with 3 117 * parameters specifying the Resultant Combined PDF file and the 2 files to 118 * combine.<br> 119 * <br> 120 * Examples:<br> 121 * java ca.bc.webarts.tools.CombineTwoPDF resultFilename file1.pdf file2.pdf<br> 122 * 123 * @param args The command line arguments 124 */ 125 public static void main(String[] args) 126 { 127 128 if (args.length >2 && 129 args[1].endsWith(".pdf") && 130 args[2].endsWith(".pdf")) 131 { 132 if (args.length >3) 133 horizOffset_ = new Float(62.0f * (new Float(args[3])).floatValue()).intValue(); 134 if (args.length >4) 135 vertOffset_ = new Float(62.0f * (new Float(args[4])).floatValue()).intValue(); 136 inFileName_ = args[1]; 137 inFileName2_ = args[2]; 138 outFileName_ = args[0]; 139 } 140 else 141 { 142 System.out.println("Filename error: "); 143 System.out.println(usage_); 144 System.exit(1); 145 } 146 147 try 148 { 149 // we create a reader for a certain document 150 System.out.println("Reading: " + inFileName_); 151 PdfReader reader = new PdfReader(inFileName_); 152 System.out.println(" : Rotated = " + reader.getPageRotation(1)); 153 154 // we retrieve the total number of pages 155 int numPages = reader.getNumberOfPages(); 156 //System.out.println("Preformating a " + numPages + 157 // " page PDF file for 2Up display. (scale=" + scale_ + " offset=" + vertOffset_ + ")"); 158 159 float width = reader.getPageSize(1).getWidth(); 160 float height = reader.getPageSize(1).getHeight(); 161 162 // step 1: creation of a document-object 163 System.out.println("New Document Size: =" + width *2.0f+" h="+height); 164 float newWidth = width; 165 float newHeight = 2.0f * height; 166 if (reader.getPageRotation(1) == 90) 167 { 168 newWidth = height; 169 newHeight = 2.0f * width; 170 } 171 Document document = 172 new Document( 173 new Rectangle(newWidth , newHeight), // these are doubled so the combined docs fit 174 0, 0, 0, 0);// Margins: left, right,top, bottom 175 176 // step 2: we create a writer that listens to the document 177 System.out.println("Writing: " + outFileName_); 178 FileOutputStream outFileStream = new FileOutputStream(outFileName_); 179 PdfWriter writer = PdfWriter.getInstance(document, outFileStream); 180 181 // step 3: we open the document 182 document.open(); 183 184 // step 4: calculate the new scaling / layout postion 185 PdfContentByte cb = writer.getDirectContent(); 186 System.out.println("There are " + numPages + 187 " pages in the document."); 188 System.out.println("Only the 1st page will be used"); 189 int currentPage = 0; 190 191 /* 192 * step 5: Start Copying the pages to the new Doc (in 2Up format) 193 */ 194 /* 195 * ******* ****************************************************** 196 */ 197 System.out.println("Page offset= -" +vertOffset_); 198 document.newPage(); 199 // Calculate the Transfor parameters to use given the scale and postion 200 scale_ = 1.0f; 201 rotation_ = Math.toRadians(360-reader.getPageRotation(1)); 202 float cosRotation = (new Float(Math.cos(rotation_))).floatValue(); 203 float sinRotation = (new Float(Math.sin(rotation_))).floatValue(); 204 float a = scale_ * cosRotation; 205 float b = scale_ * sinRotation; 206 float c = -1.0f * scale_ * sinRotation; 207 float d = scale_ * cosRotation; 208 //System.out.println("a= " +a); 209 //System.out.println("b= " +b); 210 //System.out.println("c= " +c); 211 //System.out.println("d= " +d); 212 213 // add the 1st doc page 214 PdfImportedPage firstPage = writer.getImportedPage(reader, 1); 215 cb.addTemplate(firstPage, a, b, c, d, 0, newHeight); 216 217 // add the 2nd doc page 218 reader = new PdfReader(inFileName2_); 219 PdfImportedPage secondPage = writer.getImportedPage(reader, 1); 220 cb.addTemplate(secondPage, a, b, c, d, horizOffset_, height - vertOffset_); 221 222 // step 6: we close the document 223 document.close(); 224 225 // optional launch the acroreader 226 if (launchAcroread_) 227 { 228 System.out.println("Launching acroread " + outFileName_); 229 String[] appArgs = {(new File(outFileName_)).getAbsolutePath()}; 230 new NativeAppLauncher(acroCmd_, appArgs); 231 } 232 } 233 catch (Exception de) 234 { 235 de.printStackTrace(); 236 } 237 } 238} 239