KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > it > stefanochizzolini > clown > objects > PdfStream


1 /*
2   Copyright 2006 Stefano Chizzolini. http://clown.stefanochizzolini.it
3
4   Contributors:
5     * Stefano Chizzolini (original code developer, info@stefanochizzolini.it):
6       contributed code is Copyright 2006 by Stefano Chizzolini.
7
8   This file should be part of the source code distribution of "PDF Clown library"
9   (the Program): see the accompanying README files for more info.
10
11   This Program is free software; you can redistribute it and/or modify it under
12   the terms of the GNU General Public License as published by the Free Software
13   Foundation; either version 2 of the License, or (at your option) any later version.
14
15   This Program is distributed in the hope that it will be useful, but WITHOUT ANY
16   WARRANTY, either expressed or implied; without even the implied warranty of
17   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the License for more details.
18
19   You should have received a copy of the GNU General Public License along with this
20   Program (see README files); if not, go to the GNU website (http://www.gnu.org/).
21
22   Redistribution and use, with or without modification, are permitted provided that such
23   redistributions retain the above copyright notice, license and disclaimer, along with
24   this list of conditions.
25 */

26
27 package it.stefanochizzolini.clown.objects;
28
29 import it.stefanochizzolini.clown.bytes.Buffer;
30 import it.stefanochizzolini.clown.bytes.IBuffer;
31 import it.stefanochizzolini.clown.bytes.IOutputStream;
32 import it.stefanochizzolini.clown.bytes.filters.Filter;
33 import it.stefanochizzolini.clown.files.File;
34 import java.util.Iterator JavaDoc;
35
36 /**
37   PDF stream object [PDF:1.6:3.2.7].
38 */

39 public class PdfStream
40   extends PdfDataObject
41 {
42   // <class>
43
// <dynamic>
44
// <fields>
45
private IBuffer body;
46   private PdfDictionary header;
47   // </fields>
48

49   // <constructors>
50
public PdfStream(
51     )
52   {
53     this(
54       new PdfDictionary(),
55       new Buffer()
56       );
57   }
58
59   public PdfStream(
60     PdfDictionary header
61     )
62   {
63     this(
64       header,
65       new Buffer()
66       );
67   }
68
69   public PdfStream(
70     IBuffer body
71     )
72   {
73     this(
74       new PdfDictionary(),
75       body
76       );
77   }
78
79   public PdfStream(
80     PdfDictionary header,
81     IBuffer body
82     )
83   {
84     this.header = header;
85     this.body = body;
86   }
87   // </constructors>
88

89   // <interface>
90
// <public>
91
@Override JavaDoc
92   public Object JavaDoc clone(
93     File context
94     )
95   {
96     PdfStream clone = new PdfStream(
97       (PdfDictionary)header.clone(context),
98       body.clone()
99       );
100
101     return clone;
102   }
103
104   /**
105     Gets the decoded stream body.
106   */

107   public IBuffer getBody(
108     )
109   {
110     /*
111       NOTE: Encoding filters are removed by default because they belong to a lower layer
112       (token layer), so that it's appropriate and consistent to transparently keep the object layer
113       unaware of such a facility.
114     */

115     return getBody(true);
116   }
117
118   /**
119     Gets the stream body.
120     @param decode Defines whether the body has to be decoded.
121   */

122   public IBuffer getBody(
123     boolean decode
124     )
125   {
126     if(decode)
127     {
128       // Get 'Filter' entry!
129
/*
130         NOTE: Such an entry defines possible encodings applied to the stream.
131       */

132       PdfDirectObject filterObj = header.get(PdfName.Filter);
133       // Is the stream encoded?
134
if(filterObj != null)
135       {
136         /*
137           NOTE: If the stream is encoded, we must decode it before continuing.
138         */

139         // TODO:IMPL 'DecodeParms' entry management!!!
140
PdfDataObject filterDataObj = File.resolve(filterObj);
141         if(filterDataObj instanceof PdfName) // PdfName.
142
{body.decode(Filter.get((PdfName)filterDataObj));}
143         else // MUST be PdfArray.
144
{
145           for(
146             Iterator JavaDoc<PdfDirectObject> iterator = ((PdfArray)filterDataObj).iterator();
147             iterator.hasNext();
148             filterObj = iterator.next()
149             )
150           {body.decode(Filter.get((PdfName)File.resolve(filterObj)));}
151         }
152
153         // Update 'Filter' entry!
154
header.put(PdfName.Filter,null); // The stream is free from encodings.
155
}
156     }
157
158     return body;
159   }
160
161   public PdfDictionary getHeader(
162     )
163   {return header;}
164   // </public>
165

166   // <internal>
167
@Override JavaDoc
168   int writeTo(
169     IOutputStream stream
170     )
171   {
172     int size = 0;
173     boolean unencodedBody;
174     byte[] bodyData;
175     int bodyLength;
176
177     // 1. Header.
178
// Encoding.
179
/*
180       NOTE: As the contract establishes that a stream instance should be kept
181       free from encodings in order to be editable, encoding is NOT applied to
182       the actual online stream, but to its serialized representation only.
183       That is, as encoding is just a serialization practise, it is excluded from
184       alive, instanced streams.
185     */

186     PdfDirectObject filterObj = header.get(PdfName.Filter);
187     // Is the body free from encodings?
188
if(filterObj == null) // Unencoded body.
189
{
190       /*
191         NOTE: As online representation is unencoded,
192         header entries related to the encoded stream body are temporary
193         (instrumental to the current serialization process).
194       */

195       unencodedBody = true;
196
197       // Set the filter to apply!
198
filterObj = PdfName.FlateDecode; // zlib/deflate filter.
199
// Get encoded body data applying the filter to the stream!
200
bodyData = body.encode(Filter.get((PdfName)filterObj));
201       // Set encoded length!
202
bodyLength = bodyData.length;
203       // Update 'Filter' entry!
204
header.put(PdfName.Filter,filterObj);
205     }
206     else // Encoded body.
207
{
208       unencodedBody = false;
209
210       // Get encoded body data!
211
bodyData = body.toByteArray();
212       // Set encoded length!
213
bodyLength = (int)body.getLength();
214     }
215     // Set encoded length!
216
header.put(PdfName.Length,new PdfLong(bodyLength));
217
218     size += header.writeTo(stream);
219
220     // Is the body free from encodings?
221
if(unencodedBody)
222     {
223       // Restore actual header entries!
224
((PdfLong)header.get(PdfName.Length)).setValue(body.getLength());
225       header.put(PdfName.Filter,null);
226     }
227
228     // 2. Body.
229
size += stream.write("\rstream\r");
230     size += stream.write(bodyData);
231     size += stream.write("\rendstream");
232
233     return size;
234   }
235   // </internal>
236
// </interface>
237
// </dynamic>
238
// </class>
239
}
Popular Tags