001    // $HeadURL: svn+ssh://rbezema@svn.wald.intevation.org/deegree/base/tags/2.1/src/org/deegree/framework/util/ImageUtils.java $
002    /*----------------    FILE HEADER  ------------------------------------------
003    
004     This file is part of deegree.
005     Copyright (C) 2001-2007 by:
006     EXSE, Department of Geography, University of Bonn
007     http://www.giub.uni-bonn.de/deegree/
008     lat/lon GmbH
009     http://www.lat-lon.de
010    
011     This library is free software; you can redistribute it and/or
012     modify it under the terms of the GNU Lesser General Public
013     License as published by the Free Software Foundation; either
014     version 2.1 of the License, or (at your option) any later version.
015    
016     This library is distributed in the hope that it will be useful,
017     but WITHOUT ANY WARRANTY; without even the implied warranty of
018     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
019     Lesser General Public License for more details.
020    
021     You should have received a copy of the GNU Lesser General Public
022     License along with this library; if not, write to the Free Software
023     Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
024    
025     Contact:
026    
027     Andreas Poth
028     lat/lon GmbH
029     Aennchenstr. 19
030     53115 Bonn
031     Germany
032     E-Mail: poth@lat-lon.de
033    
034     Prof. Dr. Klaus Greve
035     Department of Geography
036     University of Bonn
037     Meckenheimer Allee 166
038     53115 Bonn
039     Germany
040     E-Mail: greve@giub.uni-bonn.de
041    
042     
043     ---------------------------------------------------------------------------*/
044    package org.deegree.framework.util;
045    
046    import java.awt.image.BufferedImage;
047    import java.io.File;
048    import java.io.FileOutputStream;
049    import java.io.IOException;
050    import java.io.InputStream;
051    import java.io.OutputStream;
052    import java.net.URL;
053    
054    import javax.imageio.ImageIO;
055    import javax.media.jai.JAI;
056    import javax.media.jai.RenderedOp;
057    
058    import org.apache.batik.ext.awt.image.codec.ImageDecoderImpl;
059    import org.apache.batik.ext.awt.image.codec.PNGDecodeParam;
060    import org.apache.batik.ext.awt.image.codec.PNGImageDecoder;
061    import org.apache.batik.ext.awt.image.codec.tiff.TIFFDecodeParam;
062    import org.apache.batik.ext.awt.image.codec.tiff.TIFFImage;
063    
064    import Acme.JPM.Encoders.GifEncoder;
065    
066    import com.sun.image.codec.jpeg.JPEGCodec;
067    import com.sun.image.codec.jpeg.JPEGImageEncoder;
068    import com.sun.media.jai.codec.BMPEncodeParam;
069    import com.sun.media.jai.codec.ImageCodec;
070    import com.sun.media.jai.codec.MemoryCacheSeekableStream;
071    import com.sun.media.jai.codec.PNGEncodeParam;
072    import com.sun.media.jai.codec.SeekableStream;
073    import com.sun.media.jai.codec.TIFFEncodeParam;
074    
075    /**
076     * Some util methods for reading standard images 
077     *
078     * @author <a href="mailto:poth@lat-lon.de">Andreas Poth</a>
079     * @author last edited by: $Author: apoth $
080     *
081     * @version $Revision: 7819 $, $Date: 2007-07-24 09:48:19 +0200 (Di, 24 Jul 2007) $
082     */
083    public class ImageUtils {
084    
085        /**
086         * reads an image from the passed <tt>URL</tt> using JAI mechanism
087         * @param url address of the image
088         *
089         * @return read image
090         *
091         * @throws IOException 
092         */
093        public static BufferedImage loadImage( URL url )
094                                throws IOException {
095            InputStream is = url.openStream();
096            return loadImage( is );
097        }
098    
099        //TODO check url-@param Tag
100        /**
101         * reads an image from the passed <tt>InputStream</tt> using JAI mechanism
102         * 
103         * @param is
104         * @param url
105         *            address of the image
106         * 
107         * @return read image
108         * 
109         * @throws IOException
110         */
111        public static BufferedImage loadImage( InputStream is )
112                                throws IOException {
113            SeekableStream fss = new MemoryCacheSeekableStream( is );
114            RenderedOp ro = JAI.create( "stream", fss );
115            BufferedImage img = ro.getAsBufferedImage();
116            fss.close();
117            is.close();
118            return img;
119        }
120    
121        /**
122         * reads an image from the passed file location using JAI mechanism
123         *
124         * @param fileName 
125         *
126         * @return read imagey
127         *
128         * @throws IOException 
129         */
130        public static BufferedImage loadImage( String fileName )
131                                throws IOException {
132            return loadImage( new File( fileName ) );
133        }
134    
135        /**
136         * reads an image from the passed file location using JAI mechanism
137         *
138         * @param file 
139         *
140         * @return read imagey
141         *
142         * @throws IOException 
143         */
144        public static BufferedImage loadImage( File file )
145                                throws IOException {
146            
147            BufferedImage img = null;
148            String tmp = file.getName().toLowerCase();
149            if ( tmp.endsWith( ".tif" ) || tmp.endsWith( ".tiff" ) ) {         
150                InputStream is = file.toURL().openStream();
151                org.apache.batik.ext.awt.image.codec.SeekableStream fss = 
152                    new org.apache.batik.ext.awt.image.codec.MemoryCacheSeekableStream( is );
153                TIFFImage tiff = new TIFFImage(fss, new TIFFDecodeParam(), 0 );
154                img = RenderedOp.wrapRenderedImage( tiff ).getAsBufferedImage();
155                fss.close();
156            } else if ( tmp.endsWith( ".png" ) ) {
157                InputStream is = file.toURL().openStream();
158                ImageDecoderImpl dec = new PNGImageDecoder( is, new PNGDecodeParam() ); 
159                img = RenderedOp.wrapRenderedImage( dec.decodeAsRenderedImage() ).getAsBufferedImage();
160                is.close();
161            } else {
162                img = ImageIO.read(file); 
163            }
164    
165            return img;
166        }
167    
168        /**
169         * stores the passed image in the passed file name with defined quality
170         * 
171         * @param image
172         * @param fileName
173         * @param quality just supported for jpeg (0..1)
174         * @throws IOException
175         */
176        public static void saveImage( BufferedImage image, String fileName, float quality )
177                                throws IOException {
178            File file = new File( fileName );
179            saveImage( image, file, quality );
180        }
181    
182        /**
183         * stores the passed image in the passed file with defined quality
184         * 
185         * @param image
186         * @param file
187         * @param quality just supported for jpeg (0..1)
188         * @throws IOException
189         */
190        public static void saveImage( BufferedImage image, File file, float quality )
191                                throws IOException {
192            int pos = file.getName().lastIndexOf( '.' );
193            String ext = file.getName().substring( pos + 1, file.getName().length() ).toLowerCase();
194    
195            FileOutputStream fos = new FileOutputStream( file );
196            saveImage( image, fos, ext, quality );
197    
198        }
199    
200        /**
201         * write an image into the passed output stream. after writing the image the
202         * stream will be closed.
203         * @param image
204         * @param os
205         * @param format
206         * @param quality
207         * @throws IOException
208         */
209        public static void saveImage( BufferedImage image, OutputStream os, String format, float quality )
210                                throws IOException {
211            try {
212    
213                if ( "jpeg".equalsIgnoreCase( format ) || "jpg".equalsIgnoreCase( format ) ) {
214                    encodeJpeg( os, image, quality );
215                } else if ( "tif".equalsIgnoreCase( format ) || "tiff".equalsIgnoreCase( format ) ) {
216                    encodeTiff( os, image );
217                } else if ( "png".equalsIgnoreCase( format ) ) {
218                    encodePng( os, image );
219                } else if ( "gif".equalsIgnoreCase( format ) ) {
220                    encodeGif( os, image );
221                } else if ( "bmp".equalsIgnoreCase( format ) ) {
222                    encodeBmp( os, image );
223                } else {
224                    throw new IOException( "invalid image format: " + format );
225                }
226            } catch ( IOException e ) {
227                throw e;
228            } finally {
229                os.close();
230            }
231    
232        }
233        
234        /**
235        *
236        *
237        * @param out 
238        * @param img 
239        *
240        * @throws IOException 
241        */
242        private static synchronized void encodeGif( OutputStream out, BufferedImage img )
243                                          throws IOException {
244           GifEncoder encoder = new GifEncoder( img, out );
245           encoder.encode();
246       }
247    
248       /**
249        *
250        *
251        * @param out 
252        * @param img 
253        *
254        * @throws IOException 
255        */
256       private static synchronized void encodeBmp( OutputStream out, BufferedImage img )
257                                          throws IOException {
258           BMPEncodeParam encodeParam = new BMPEncodeParam();
259    
260           com.sun.media.jai.codec.ImageEncoder encoder = ImageCodec.createImageEncoder( "BMP", out, 
261                                                                                         encodeParam );
262    
263           encoder.encode( img );
264       }
265    
266       /**
267        *
268        *
269        * @param out 
270        * @param img 
271        *
272        * @throws IOException 
273        */
274       private static synchronized void encodePng( OutputStream out, BufferedImage img )
275                                          throws IOException {
276           PNGEncodeParam encodeParam = PNGEncodeParam.getDefaultEncodeParam( img );
277           
278           if ( encodeParam instanceof PNGEncodeParam.Palette ) {
279               PNGEncodeParam.Palette p = (PNGEncodeParam.Palette)encodeParam;       
280               byte[] b = new byte[]{-127};        
281               p.setPaletteTransparency(b);
282           }
283                   
284           com.sun.media.jai.codec.ImageEncoder encoder = 
285               ImageCodec.createImageEncoder("PNG", out, encodeParam);
286           encoder.encode( img.getData(), img.getColorModel() );
287       }
288    
289       /**
290        *
291        *
292        * @param out 
293        * @param img 
294        *
295        * @throws IOException 
296        */
297       private static synchronized void encodeTiff( OutputStream out, BufferedImage img )
298                                           throws IOException {
299           TIFFEncodeParam encodeParam = new TIFFEncodeParam();
300    
301           com.sun.media.jai.codec.ImageEncoder encoder = ImageCodec.createImageEncoder( "TIFF", out, 
302                                                                                         encodeParam );
303    
304           encoder.encode( img );        
305       }
306    
307       /**
308        *
309        *
310        * @param out 
311        * @param img 
312        * @param quality 
313        *
314        * @throws IOException 
315        */
316       private static synchronized void encodeJpeg( OutputStream out, BufferedImage img, float quality )
317                                           throws IOException {
318    
319           // encode JPEG
320           JPEGImageEncoder encoder = JPEGCodec.createJPEGEncoder( out );
321           com.sun.image.codec.jpeg.JPEGEncodeParam jpegParams = encoder.getDefaultJPEGEncodeParam( 
322                                                                         img );
323           jpegParams.setQuality( quality, false );
324           encoder.setJPEGEncodeParam( jpegParams );
325    
326           encoder.encode( img );
327       }
328    
329    }