1 /*
2 * $Id: PRStream.java 3538 2008-07-08 13:08:04Z blowagie $
3 *
4 * Copyright 2001, 2002 by Paulo Soares.
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.ByteArrayOutputStream;
53 import java.io.IOException;
54 import java.io.OutputStream;
55 import java.util.zip.Deflater;
56 import java.util.zip.DeflaterOutputStream;
57
58 import com.lowagie.text.Document;
59 import com.lowagie.text.ExceptionConverter;
60
61 public class PRStream extends PdfStream {
62
63 protected PdfReader reader;
64 protected int offset;
65 protected int length;
66
67 //added by ujihara for decryption
68 protected int objNum = 0;
69 protected int objGen = 0;
70
71 public PRStream(PRStream stream, PdfDictionary newDic) {
72 reader = stream.reader;
73 offset = stream.offset;
74 length = stream.length;
75 compressed = stream.compressed;
76 compressionLevel = stream.compressionLevel;
77 streamBytes = stream.streamBytes;
78 bytes = stream.bytes;
79 objNum = stream.objNum;
80 objGen = stream.objGen;
81 if (newDic != null)
82 putAll(newDic);
83 else
84 hashMap.putAll(stream.hashMap);
85 }
86
87 public PRStream(PRStream stream, PdfDictionary newDic, PdfReader reader) {
88 this(stream, newDic);
89 this.reader = reader;
90 }
91
92 public PRStream(PdfReader reader, int offset) {
93 this.reader = reader;
94 this.offset = offset;
95 }
96
97 public PRStream(PdfReader reader, byte conts[]) {
98 this(reader, conts, DEFAULT_COMPRESSION);
99 }
100
101 /**
102 * Creates a new PDF stream object that will replace a stream
103 * in a existing PDF file.
104 * @param reader the reader that holds the existing PDF
105 * @param conts the new content
106 * @param compressionLevel the compression level for the content
107 * @since 2.1.3 (replacing the existing constructor without param compressionLevel)
108 */
109 public PRStream(PdfReader reader, byte[] conts, int compressionLevel) {
110 this.reader = reader;
111 this.offset = -1;
112 if (Document.compress) {
113 try {
114 ByteArrayOutputStream stream = new ByteArrayOutputStream();
115 DeflaterOutputStream zip = new DeflaterOutputStream(stream, new Deflater(compressionLevel));
116 zip.write(conts);
117 zip.close();
118 bytes = stream.toByteArray();
119 }
120 catch (IOException ioe) {
121 throw new ExceptionConverter(ioe);
122 }
123 put(PdfName.FILTER, PdfName.FLATEDECODE);
124 }
125 else
126 bytes = conts;
127 setLength(bytes.length);
128 }
129
130 /**
131 * Sets the data associated with the stream, either compressed or
132 * uncompressed. Note that the data will never be compressed if
133 * Document.compress is set to false.
134 *
135 * @param data raw data, decrypted and uncompressed.
136 * @param compress true if you want the stream to be compresssed.
137 * @since iText 2.1.1
138 */
139 public void setData(byte[] data, boolean compress) {
140 setData(data, compress, DEFAULT_COMPRESSION);
141 }
142
143 /**
144 * Sets the data associated with the stream, either compressed or
145 * uncompressed. Note that the data will never be compressed if
146 * Document.compress is set to false.
147 *
148 * @param data raw data, decrypted and uncompressed.
149 * @param compress true if you want the stream to be compresssed.
150 * @param compressionLevel a value between -1 and 9 (ignored if compress == false)
151 * @since iText 2.1.3
152 */
153 public void setData(byte[] data, boolean compress, int compressionLevel) {
154 remove(PdfName.FILTER);
155 this.offset = -1;
156 if (Document.compress && compress) {
157 try {
158 ByteArrayOutputStream stream = new ByteArrayOutputStream();
159 DeflaterOutputStream zip = new DeflaterOutputStream(stream, new Deflater(compressionLevel));
160 zip.write(data);
161 zip.close();
162 bytes = stream.toByteArray();
163 this.compressionLevel = compressionLevel;
164 }
165 catch (IOException ioe) {
166 throw new ExceptionConverter(ioe);
167 }
168 put(PdfName.FILTER, PdfName.FLATEDECODE);
169 }
170 else
171 bytes = data;
172 setLength(bytes.length);
173 }
174
175 /**Sets the data associated with the stream
176 * @param data raw data, decrypted and uncompressed.
177 */
178 public void setData(byte[] data) {
179 setData(data, true);
180 }
181
182 public void setLength(int length) {
183 this.length = length;
184 put(PdfName.LENGTH, new PdfNumber(length));
185 }
186
187 public int getOffset() {
188 return offset;
189 }
190
191 public int getLength() {
192 return length;
193 }
194
195 public PdfReader getReader() {
196 return reader;
197 }
198
199 public byte[] getBytes() {
200 return bytes;
201 }
202
203 public void setObjNum(int objNum, int objGen) {
204 this.objNum = objNum;
205 this.objGen = objGen;
206 }
207
208 int getObjNum() {
209 return objNum;
210 }
211
212 int getObjGen() {
213 return objGen;
214 }
215
216 public void toPdf(PdfWriter writer, OutputStream os) throws IOException {
217 byte[] b = PdfReader.getStreamBytesRaw(this);
218 PdfEncryption crypto = null;
219 if (writer != null)
220 crypto = writer.getEncryption();
221 PdfObject objLen = get(PdfName.LENGTH);
222 int nn = b.length;
223 if (crypto != null)
224 nn = crypto.calculateStreamSize(nn);
225 put(PdfName.LENGTH, new PdfNumber(nn));
226 superToPdf(writer, os);
227 put(PdfName.LENGTH, objLen);
228 os.write(STARTSTREAM);
229 if (length > 0) {
230 if (crypto != null && !crypto.isEmbeddedFilesOnly())
231 b = crypto.encryptByteArray(b);
232 os.write(b);
233 }
234 os.write(ENDSTREAM);
235 }
236 }