Archivo TIF de Java ImageIO-ext dañado cuando se lee

Estoy intentando mostrar un .tifarchivo en Java utilizando un número mínimo de bibliotecas adicionales:

import javax.imageio.ImageIO;
import javax.swing.ImageIcon;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.WindowConstants;

import javax.media.jai.widget.*;
import it.geosolutions.imageio.utilities.*;
import it.geosolutions.imageioimpl.plugins.tiff.*;
import com.sun.media.imageioimpl.common.*;

public static void main(String[] args) {
    try {
        File f = new File("image.tif");  
        BufferedImage tif = ImageIO.read(f);  
        ImageIcon ic = new ImageIcon(tif);  
        JFrame frame = new JFrame();  
        frame.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);  
        JLabel label = new JLabel(ic);  
        frame.add(label);  
        frame.setVisible(true);  
    } catch (IOException e) {
        e.printStackTrace();
    }
}

Las bibliotecas que estoy usando son:

 jai-core-1.1.3.jar
 jai-imageio-1.1.jar
 imageio-ext-tiff.1.1.3.jar
 imageio-ext-utilities.1.1.3.jar

Desde aquí: http://java.net/projects/imageio-ext (enlace de descargas en el lado derecho)

Sin embargo, la imagen mostrada es: tif corrupto que definitivamente no es la imagen original. Tampoco se arrojan errores que yo sepa. Además, la imagen original está bien y no cambia.

Sin embargo, el código original es pequeño. En realidad no uso las imageio-extimportaciones, pero el programa fallará sin ellas. Tampoco he usado imageio-extantes tampoco.

¡Por favor ayuda! Necesito poder usar .tifimágenes en Java sin instalar software.

Respuesta 1

Si ya usa todas las bibliotecas JAI / ImageIO, puede probar lo siguiente (que funciona bien para mí):

import com.sun.media.jai.codec.FileSeekableStream;
import com.sun.media.jai.codec.ImageCodec;
import com.sun.media.jai.codec.ImageDecoder;

// This function is minimal, you should add exceptions and error handling
public RenderedImage read(String filename)
    FileSeekableStream fss = new FileSeekableStream(filename);
    ImageDecoder decoder = ImageCodec.createImageDecoder("tiff", fss, null);
    RenderedImage image = decoder.decodeAsRenderedImage()
    fss.close();
    return image;
}

Si necesita un en BufferedImagelugar de un RenderedImage, la única solución que encontré es usar esta función:

public static BufferedImage Rendered2Buffered(RenderedImage image) {
    BufferedImage bi = new BufferedImage(image.getWidth(), image.getHeight(), image.getSampleModel().getDataType());
    bi.setData(image.getData());
    return bi;
}

Sin embargo, tenga cuidado, por lo image.getSampleModel().getDataType()general, devuelve a BufferedImage.TYPE_CUSTOM, lo que hace que sea imposible BufferedImageque se cree. En mi caso, tuve que "adivinar" el tipo de acuerdo con el tamaño de muestra devuelto por image.getSampleModel().getSampleSize(0)(porque sé el formato de imagen con el que estoy trabajando). Si conoces una mejor manera de transformar a RenderedImagea a BufferedImage, por favor, ilumíname :)

Respuesta: 2

Tienes razón al pensar que necesitas las bibliotecas JAI para decodificar y usar archivos TIFF, pero aunque las hayas importado, ¡en realidad no las estás usando!

Aquí hay un breve tutorial que muestra cómo crear un objeto TIFFDecodeParam (de la biblioteca JAI), y luego usarlo para decodificar (y mostrar) una imagen TIFF.

También puede encontrar útil la Biblioteca API JAI .

Respuesta: 3

Estoy tratando de enviar un correo electrónico utilizando la API de correo Java. Pero mi texto de correo electrónico es demasiado grande para ser almacenado en una Cadena. ¿Hay alguna forma de enviar un correo electrónico con algo así como una matriz de cadenas o cualquier colección?

Estoy trabajando en un proyecto en el trabajo, y me encargaron implementar una biblioteca Java Swing personalizada que registre un evento en un archivo cada vez que un usuario interactúe con un componente Swing. En otra ...

Creé la clase JFrame en Netbeans y, usando el generador, agregué jPanel. También tengo clase, que extiende JPanel. Ahora quiero crear un objeto de esta clase y agregarlo en el lugar donde está mi Panel ...

Ni las interfaces ni las clases abstractas pueden dictar a las subclases el tipo de constructor a implementar (consulte ¿Cómo puedo forzar la definición de un Constructor en todas las subclases de mi clase abstracta?) Ahora ...