Another tiff problem!
Hi all,
I'm using the following code to load in a tiff and output it as a png. Something weird seems to happen to the image when it is loaded in. The color space seems to go awry!
package com.peoplesarchive.sandbox;
import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.RenderingHints;
import java.awt.image.BufferedImage;
import java.awt.image.ImageObserver;
import java.io.File;
import java.util.Iterator;
import javax.imageio.ImageIO;
import javax.imageio.ImageReader;
import javax.imageio.ImageWriter;
import javax.imageio.stream.FileImageOutputStream;
import javax.imageio.stream.ImageInputStream;
import javax.swing.ImageIcon;
import javax.swing.JFrame;
import javax.swing.JLabel;
publicclass DiscLabelGeneratorimplements ImageObserver{
publicvoid generateDiscLabel(String category, String occupation, String name, String runnungTime, String discFile, String personFile, String opFile)throws Exception{
Image bgImage = (new ImageIcon(discFile)).getImage();
BufferedImage personImage;
if (personFile.endsWith(".tif") || personFile.endsWith(".tiff")){
Iterator rs = ImageIO.getImageReadersByFormatName("tiff");
ImageReader ir = (ImageReader) rs.next();
File srcFile =new File(personFile);
ImageInputStream iis = ImageIO.createImageInputStream(srcFile);
ir.setInput(iis);
personImage = ir.read(0);
}
else{
personImage = (BufferedImage)(new ImageIcon(personFile)).getImage();
}
JFrame frame =new JFrame("Preview Image");
frame.getContentPane().add(new JLabel(new ImageIcon(personImage)));
frame.pack();
frame.setVisible(true);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
System.out.println(personImage.getColorModel());
BufferedImage opImage =new BufferedImage(1520, 1520, BufferedImage.TYPE_INT_ARGB_PRE);
//if (personImage.getWidth(this) == -1) {
//throw new Exception("image invalid!");
//}
Graphics2D graphics = opImage.createGraphics();
graphics.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
graphics.drawImage(personImage, 0, 481,this);
//graphics.drawImage(bgImage, 0, 0, 1520, 1520, 0, 0, 1520, 1520, this);
//org.apache.batik.ext.awt.image.codec.
Iterator rs = ImageIO.getImageWritersByFormatName("png");
if (!rs.hasNext()){
thrownew Exception("no writer available!");
}
ImageWriter iw = (ImageWriter) rs.next();
FileImageOutputStream os =new FileImageOutputStream(new File(opFile));
iw.setOutput(os);
//iw.write(opImage);
iw.write(personImage);
os.flush();
os.close();
}
publicboolean imageUpdate(Image img,int infoflags,int x,int y,int width,int height){
returnfalse;
}
publicstaticvoid main(String[] args)throws Exception{
DiscLabelGenerator gen =new DiscLabelGenerator();
gen.generateDiscLabel("Science","Software Developer","Paul Loy","752 minutes","disc_template2.gif","63.tiff","63.png");
}
}
the original image can be found at http://www.keteracel.com/outimg/63.tiff and the result can be found at http://www.keteracel.com/outimg/63.png
I'm on Mac OSX 10.3.9 so I can only get JDK 1.4.2_09-233 build 1.4.2-56 and I can't download the latest jai as it doesn't have native Mac binaries nor an ant build for Macs. Any help on where I could find a different tiff codec or a way to modify the color space would be helpful,
Cheers,
Paul.
[6274 byte] By [
foobart2a] at [2007-11-26 18:10:58]

# 1
ok, fixed it be using Quicktime to load tiffs:
package com.keteracel.qtutils;
import java.awt.Image;
import java.io.File;
import java.io.IOException;
import javax.imageio.ImageIO;
import javax.swing.ImageIcon;
import quicktime.QTException;
import quicktime.QTSession;
import quicktime.app.view.QTFactory;
import quicktime.io.QTFile;
import quicktime.std.StdQTConstants4;
import quicktime.std.image.GraphicsExporter;
import quicktime.std.image.GraphicsImporter;
/**
* Little image reading helper class. *WARNING* this class is not threadsafe. There is no way to know
* when finalize() will be called due to the nature of the GC. As such you should either only use one
* instance of this class in your programs or initialise and clean up quicktime yourself.
* @author Paul Andrew Loy http://www.keteracel.com/paul
* (c) 2007 KETERACEL.COM LTD
* We're giving this away under a GPL license.
*
*/
public class KeteracelImageReader {
private boolean closeQuicktime = false;
/**
* Creates an image reader. Equivalent to calling KeteracelImageReader(false);
* @throws KeteracelImageException
*/
public KeteracelImageReader() throws KeteracelImageException {
this(false);
}
/**
* Creates an image reader.
* @param quicktimerequired if this is the only class that needs quicktime, set this to true to clean up Quicktime after use.
* @throws KeteracelImageException if quicktime cannot be instantiated.
*/
public KeteracelImageReader(boolean quicktimerequired) throws KeteracelImageException {
if (quicktimerequired) {
try {
QTSession.open();
} catch (QTException e) {
throw new KeteracelImageException("Quictime failed to load. Please ensure Quicktime is installed.", e);
}
closeQuicktime = true;
}
}
/**
* If this we decided that we're not using Quicktime anywhere else
* the let's free up some resources.
*/
protected void finalize() throws Throwable {
if (closeQuicktime) {
QTSession.close();
}
super.finalize();
}
/**
* Loads an image. If the filename is a tiff it uses Quicktime to load
* the image as Quicktime's tiff codec is better than jdk1.4.2's tiff
* codec.
* @param image the file to try to load.
* @return an Image
* @throws KeteracelImageException if the file cannot be loaded.
*/
public final Image readImage(String image) throws KeteracelImageException {
Image img;
if (image.endsWith(".tif") || image.endsWith(".tiff")) {
img = loadTiff(image);
}
else {
img = (new ImageIcon(image)).getImage();
}
return img;
}
/**
* Loads a TIFF file in using the Quicktime GraphicsImporter and
* GraphicsExporter components.
* @param filename the file to read in.
* @return an Image
* @throws KeteracelImageException if the file cannot be loaded.
*/
public final Image loadTiff(String filename) throws KeteracelImageException {
QTFile qtimage = null;
try {
qtimage = new QTFile(QTFactory.findAbsolutePath(filename));
} catch (IOException e) {
throw new KeteracelImageException("File '" + filename + "' could not be read. Make sure the file exists and has the correct permissions!", e);
}
GraphicsImporter importer = null;
try {
importer = new GraphicsImporter(qtimage);
} catch (QTException e) {
throw new KeteracelImageException("Quicktime import failed. File format is incorrect.", e);
}
try {
GraphicsExporter exporter = new GraphicsExporter(StdQTConstants4.kQTFileTypePNG);
exporter.setInputGraphicsImporter(importer);
exporter.setOutputFile(new QTFile(new File("tmp.png")));
exporter.doExport();
} catch (QTException e) {
throw new KeteracelImageException("Quicktime export failed. Make sure the root folder (" + (new File(".")).getAbsolutePath() + ") is not write protected.", e);
}
try {
return ImageIO.read(new File("tmp.png"));
} catch (IOException e) {
throw new KeteracelImageException("Temp file failed to load.", e);
}
}
}
and the exception class is:
package com.keteracel.qtutils;
public class KeteracelImageException extends Exception {
public KeteracelImageException(String message, Exception parent) {
super(message, parent);
}
}