in tools/src/main/java/org/apache/pdfbox/tools/imageio/ImageIOUtil.java [204:329]
public static boolean writeImage(BufferedImage image, String formatName, OutputStream output,
int dpi, float compressionQuality, String compressionType) throws IOException
{
ImageOutputStream imageOutput = null;
ImageWriter writer = null;
try
{
// find suitable image writer
Iterator<ImageWriter> writers = ImageIO.getImageWritersByFormatName(formatName);
ImageWriteParam param = null;
IIOMetadata metadata = null;
// Loop until we get the best driver, i.e. one that supports
// setting dpi in the standard metadata format; however we'd also
// accept a driver that can't, if a better one can't be found
while (writers.hasNext())
{
if (writer != null)
{
writer.dispose();
}
writer = writers.next();
if (writer != null)
{
param = writer.getDefaultWriteParam();
metadata = writer.getDefaultImageMetadata(new ImageTypeSpecifier(image), param);
if (metadata != null
&& !metadata.isReadOnly()
&& metadata.isStandardMetadataFormatSupported())
{
break;
}
}
}
if (writer == null)
{
LOG.error("No ImageWriter found for '{}' format", formatName);
LOG.error("Supported formats: {}", Arrays.toString(ImageIO.getWriterFormatNames()));
return false;
}
boolean isTifFormat = formatName.toLowerCase().startsWith("tif");
// compression
if (param != null && param.canWriteCompressed())
{
param.setCompressionMode(ImageWriteParam.MODE_EXPLICIT);
if (isTifFormat)
{
if ("".equals(compressionType))
{
// default logic
TIFFUtil.setCompressionType(param, image);
}
else
{
param.setCompressionType(compressionType);
if (compressionType != null)
{
param.setCompressionQuality(compressionQuality);
}
}
}
else
{
param.setCompressionType(param.getCompressionTypes()[0]);
param.setCompressionQuality(compressionQuality);
}
}
if (metadata != null)
{
if (isTifFormat)
{
// TIFF metadata
TIFFUtil.updateMetadata(metadata, image, dpi);
}
else if ("jpeg".equalsIgnoreCase(formatName) || "jpg".equalsIgnoreCase(formatName))
{
// This segment must be run before other meta operations,
// or else "IIOInvalidTreeException: Invalid node: app0JFIF"
// The other (general) "meta" methods may not be used, because
// this will break the reading of the meta data in tests
JPEGUtil.updateMetadata(metadata, dpi);
}
else
{
// write metadata is possible
if (!metadata.isReadOnly() && metadata.isStandardMetadataFormatSupported())
{
setDPI(metadata, dpi, formatName);
}
}
}
if (metadata != null && formatName.equalsIgnoreCase("png") && hasICCProfile(image))
{
// add ICC profile
IIOMetadataNode iccp = new IIOMetadataNode("iCCP");
ICC_Profile profile = ((ICC_ColorSpace) image.getColorModel().getColorSpace())
.getProfile();
iccp.setUserObject(getAsDeflatedBytes(profile));
iccp.setAttribute("profileName", "unknown");
iccp.setAttribute("compressionMethod", "deflate");
Node nativeTree = metadata.getAsTree(metadata.getNativeMetadataFormatName());
nativeTree.appendChild(iccp);
metadata.mergeTree(metadata.getNativeMetadataFormatName(), nativeTree);
}
// write
imageOutput = ImageIO.createImageOutputStream(output);
writer.setOutput(imageOutput);
writer.write(null, new IIOImage(image, null, metadata), param);
}
finally
{
if (writer != null)
{
writer.dispose();
}
if (imageOutput != null)
{
imageOutput.close();
}
}
return true;
}