File APIs for Java Developers
Manipulate DOC, XLS, PPT, PDF and many others from your application.
The moose likes Java in General and the fly likes Splitting Tiff file with JAI taking more time Big Moose Saloon
  Search | Java FAQ | Recent Topics | Flagged Topics | Hot Topics | Zero Replies
Register / Login
JavaRanch » Java Forums » Java » Java in General
Bookmark "Splitting Tiff file with JAI taking more time" Watch "Splitting Tiff file with JAI taking more time" New topic

Splitting Tiff file with JAI taking more time

Janardhan Kotha

Joined: Feb 01, 2006
Posts: 14

I am using Java Advanced Imaging (JAI) API to split a tiff file into mutliple files. Our tiff file is in COMPRESSION_GROUP4.

To split the file in memory, we are using ImageDecoder & ImageEncoder. Here if the original doc is 10 pages and we may want to split it as let us say 1-3, 4-5, 6-9, 10-10 pages, the decoder reads them as render image and encode as tiff using COMPRESSION_GROUP4. Decompression and compression is taking more time. Is there any way to get the compressed images as it is?

Please have a look at the source code below.

/* This is a helper class that takes a tiff byte stream path and
page ranges and returns a byte array for every page range */
public static List splitTiff(byte[] bytes, List pageRanges) throws AppException, Exception {
long startTime = System.currentTimeMillis();

final String methodName = "splitTiff";
DbHelper dbh = new DbHelper(logger, CLASS_NAME, methodName);

List splittedDocBytes = new ArrayList();

dbh.logMessage("Instantiating tiff decoder");
RenderedImage image;
TIFFDecodeParam param = new TIFFDecodeParam();
ImageDecoder decoder = ImageCodec.createImageDecoder("TIFF", new ByteArrayInputStream(bytes), param);
int pageCount = decoder.getNumPages();

if ( pageRanges != null && pageCount > 0 ) {
List docPageRange;
int startPage = -1;
int endPage = -1;
int docCount = 0;

for (Iterator iter = pageRanges.iterator(); iter.hasNext(); ++docCount) {
docPageRange = (List);
startPage = ((Integer)docPageRange.get(0)).intValue();
endPage = ((Integer)docPageRange.get(1)).intValue();

dbh.logMessage("Document "+docCount +" - startpage=" + startPage + " - endpage=" + endPage);

if ( startPage < 0 || startPage > pageCount
|| endPage < 0 || endPage > pageCount ){
throw new AppException(

/* swap start & end pages if they are swapped */
if ( startPage > endPage ){
dbh.logMessage("swapping the start & end pages");
int temp = startPage;
startPage = endPage;
endPage = temp;

dbh.logMessage("extracting the page as rendered images from main document");
List pages = new ArrayList((endPage-startPage+1));
for (int pageIndex = startPage; pageIndex <= endPage; ++pageIndex) {
image = decoder.decodeAsRenderedImage((pageIndex-1));

dbh.logMessage("getting the binary data of rendered images...");
byte[] pageBytes = getBytesForMultiPageTIFF(pages, dbh);

dbh.logMessage("adding binary data to return list...");

long endTime = System.currentTimeMillis();
dbh.logMessage("Time taken (ms):" + (endTime-startTime));

return splittedDocBytes;

/* It converts vector of buffered images to multi Page Tiff image and
* returns the byte array out of it. */
private static byte[] getBytesForMultiPageTIFF(List images, DbHelper dbh) throws IOException {
long startTime = System.currentTimeMillis();

final String methodName = "getBytesForMultiPageTIFF";

byte[] bytes = new byte[0];

/* check if there are any images?? */
if (images.size() < 1)
return bytes;

/*Get the first page and remove it from list*/
dbh.logMessage("Getting the first rendered page/image");
RenderedImage firstImage = (RenderedImage) images.get(0);

ByteArrayOutputStream out = null;

try {
/* We need to capture the data in byte array */
dbh.logMessage("instantiating byte-array-outputstream to write binary data of images");
out = new ByteArrayOutputStream();

/*Use tiffencoder and write the data to byte array output stream. */
dbh.logMessage("instantiating tiff encoder to encode binary data");
TIFFEncodeParam param = new TIFFEncodeParam();
ImageEncoder encoder = ImageCodec.createImageEncoder("TIFF", out, param);

/*Set the pages other than first page*/
dbh.logMessage("setting all the pages to be written other than first-page");
if (images.size() > 0) {

/*Encode the first image.*/
dbh.logMessage("encode first page");


/* Get the data in bytes */
dbh.logMessage("get the data in bytes");
bytes = out.toByteArray();

} catch (IOException ex) {
throw ex;
if ( null != out ){

long endTime = System.currentTimeMillis();
dbh.logMessage("Time taken (ms):" + (endTime-startTime));
return bytes;

Appreciate your help.

[ February 01, 2006: Message edited by: Janardhan Kotha ]
Ernest Friedman-Hill
author and iconoclast

Joined: Jul 08, 2003
Posts: 24199


Welcome to JavaRanch!

Please don't post the same question to multiple forums; I've deleted your other copy. See here for an explanation.

Have you done any profiling? Do you know where the time is going?

[Jess in Action][AskingGoodQuestions]
Janardhan Kotha

Joined: Feb 01, 2006
Posts: 14

My apologies for posting in different forums. I haven't done the profiling, but as per the timings(in millis) from my log file, it is taking more time in encoder.encode().

Thanks in advance.
Rao Kotha.
I agree. Here's the link:
subject: Splitting Tiff file with JAI taking more time
It's not a secret anymore!