/* * Copyright (c) 2008 Los Alamos National Security, LLC. * * Los Alamos National Laboratory * Research Library * Digital Library Research & Prototyping Team * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 2.1 of the License, or (at your option) any later version. * * This library is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public * License along with this library; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ package gov.lanl.adore.djatoka.kdu.jni; import gov.lanl.adore.djatoka.DjatokaDecodeParam; import gov.lanl.adore.djatoka.DjatokaException; import gov.lanl.adore.djatoka.IExtract; import gov.lanl.adore.djatoka.util.ImageRecord; import gov.lanl.adore.djatoka.util.JP2ImageInfo; import java.awt.image.BufferedImage; import java.io.File; import java.io.IOException; import java.io.InputStream; import kdu_jni.Jp2_family_src; import kdu_jni.Jp2_input_box; import kdu_jni.Jp2_locator; import kdu_jni.Jp2_source; import kdu_jni.KduException; import kdu_jni.Kdu_channel_mapping; import kdu_jni.Kdu_codestream; import kdu_jni.Kdu_compressed_source; import kdu_jni.Kdu_coords; import kdu_jni.Kdu_dims; import org.apache.log4j.Logger; /** * Uses Kakadu Java Native Interface to extract JP2 regions. * This is modified port of the kdu_expand app. * @author Ryan Chute * */ public class KduExtractJNI implements IExtract { private static Logger logger = Logger.getLogger(KduExtractJNI.class); /** * Returns JPEG 2000 props in ImageRecord * @param r ImageRecord containing absolute file path of JPEG 2000 image file. * @return a populated ImageRecord object * @throws DjatokaException */ public final ImageRecord getMetadata(ImageRecord r) throws DjatokaException { if (!new File(r.getImageFile()).exists()) throw new DjatokaException("Image Does Not Exist"); Jp2_source inputSource = new Jp2_source(); Kdu_compressed_source kduIn = null; Jp2_family_src jp2_family_in = new Jp2_family_src(); Jp2_locator loc = new Jp2_locator(); try { jp2_family_in.Open(r.getImageFile(), true); inputSource.Open(jp2_family_in, loc); inputSource.Read_header(); kduIn = inputSource; Kdu_codestream codestream = new Kdu_codestream(); codestream.Create(kduIn); Kdu_channel_mapping channels = new Kdu_channel_mapping(); if (inputSource.Exists()) channels.Configure(inputSource, false); else channels.Configure(codestream); int ref_component = channels.Get_source_component(0); int minLevels = codestream.Get_min_dwt_levels(); int minLayers= codestream.Get_max_tile_layers(); Kdu_dims image_dims = new Kdu_dims(); codestream.Get_dims(ref_component, image_dims); Kdu_coords imageSize = image_dims.Access_size(); r.setWidth(imageSize.Get_x()); r.setHeight(imageSize.Get_y()); r.setDWTLevels(minLevels); channels.Native_destroy(); if (codestream.Exists()) codestream.Destroy(); kduIn.Native_destroy(); inputSource.Native_destroy(); jp2_family_in.Native_destroy(); } catch (KduException e) { throw new DjatokaException(e); } return r; } public final String[] getXMLBox(ImageRecord r) throws DjatokaException { String[] xml = null; try { if (r.getImageFile() == null && r.getObject() != null && r.getObject() instanceof InputStream) { xml = new JP2ImageInfo((InputStream) r.getObject()).getXmlDocs(); } else { xml = new JP2ImageInfo(new File(r.getImageFile())).getXmlDocs(); } } catch (IOException e) { logger.error(e, e); } return xml; } /** * Extracts region defined in DjatokaDecodeParam as BufferedImage * @param input absolute file path of JPEG 2000 image file. * @param params DjatokaDecodeParam instance containing region and transform settings. * @return extracted region as a BufferedImage * @throws DjatokaException */ public BufferedImage process(String input, DjatokaDecodeParam params) throws DjatokaException { KduExtractProcessorJNI decoder = new KduExtractProcessorJNI(input, params); return decoder.extract(); } /** * Extracts region defined in DjatokaDecodeParam as BufferedImage * @param input InputStream containing a JPEG 2000 image bitstream. * @param params DjatokaDecodeParam instance containing region and transform settings. * @return extracted region as a BufferedImage * @throws DjatokaException */ public BufferedImage process(InputStream input, DjatokaDecodeParam params) throws DjatokaException { KduExtractProcessorJNI decoder = new KduExtractProcessorJNI(input, params); return decoder.extract(); } /** * Extracts region defined in DjatokaDecodeParam as BufferedImage * @param input ImageRecord wrapper containing file reference, inputstream, etc. * @param params DjatokaDecodeParam instance containing region and transform settings. * @return extracted region as a BufferedImage * @throws DjatokaException */ public BufferedImage process(ImageRecord input, DjatokaDecodeParam params) throws DjatokaException { if (input.getImageFile() != null) return process(input, params); else if (input.getObject() != null && (input.getObject() instanceof InputStream)) return process((InputStream) input.getObject(), params); else throw new DjatokaException( "File not defined and Input Object Type " + input.getObject().getClass().getName() + " is not supported"); } }