AWARE [SYSTEMS] Imaging expertise for the Delphi developer
AWare Systems, Imaging expertise for the Delphi developer, Home TIFF and LibTiff Mailing List Archive

LibTiff Mailing List

TIFF and LibTiff Mailing List Archive
July 2007

Previous Thread
Next Thread

Previous by Thread
Next by Thread

Previous by Date
Next by Date


The TIFF Mailing List Homepage
This list is run by Frank Warmerdam
Archive maintained by AWare Systems

Valid HTML 4.01!


2007.07.13 16:19 "Re: Bit shifting and rotating of TIFF images", by Richard Nolde
2007.07.14 12:39 "Re: Bit shifting and rotating of TIFF images", by Oliver Geisen
2007.07.14 16:03 "Re: Bit shifting and rotating of TIFF images", by Bob Friesenhahn
2007.07.16 04:57 "Image Roation by 180 degrees", by Richard Nolde
2007.07.17 09:32 "Re: Bit shifting and rotating of TIFF images", by Oliver Geisen
2007.07.17 12:10 "Re: Bit shifting and rotating of TIFF images", by <>
2007.07.18 00:33 "Re: Bit shifting and rotating of TIFF images", by Chris Cox
2007.07.20 04:26 "Bit shifts vs lookup tables", by Richard Nolde

2007.07.16 04:57 "Image Roation by 180 degrees", by Richard Nolde

Oliver wrote:

>I found your code, compiled it, and it worked well, good work!

>But allow me some questions/conclusions about that:
>What i want to do is, image rotation by 180 degrees only.
>The whole point in processing images with libtiff is that one have  
>only a limited part of the image inside a memoryblock to work with.
>This is an advantage because some images (our own also) will get very  
>Special care must be taken if imagedata is bilevel (1 bit per pixel)  
>but converting all the data  into an 8 bit pixel, process it and  
>reconvert it to 1 bit pixels seems to be clumsy.

  I do not convert each pixel into a full byte and the rewrite it.
If you look at the code in tiffcrop, you will see that it is all done
with tight loops addressing one byte at a time, but not expanding each
bit to a full byte.  It involves a series of shifts and masks, tracking
the bit offset within the source and destination bytes and carrying the 
"extra" bits over to the next byte each time for non-aligned scenarios.
There are separate cases for handling byte aligned and non-aligned data
to optimize the performance whenever possible. If you are going to use 
a lookup table, you might as well reverse the whole byte in one operation, 
but again this only works for the simple case of byte aligned data. I 
handle the cases where the start and/or ending pixels are not byte aligned 
as well as the simple cases where one or both are byte aligned. For 90 or 
270 degrees you are reading one byte at a time but writing each bit of 
that byte to a different address in the output raster, hence the 
performance degradation.

The current limitation of my code is that I read an entire image into 
memory in one pass. It handles strips and tiles for you. However, since the
rotation code works only on input and output buffer pointers, it has no
way to know whether you are calling it with one scanline or the whole 
image. Just remove the outer loop that iterates over the whole image and
pass it one row at a time.  This will work fine for any rotation as long 
as you allocate the entire output buffer before the first call and add the
additional parameters to track the current row or column which you must 
do in your calling function.  You would just be moving the outer loop from
my rotation function into your calling function and reading the input 
image one line at a time instead of all at once. Unless the image is very
large and causes swapping on your system, I doubt that the change will 
make much difference as most of the time is spent in reading and writing
the image to/from disk. 

For tiles, I think you will have to read and track enough tiles to make up 
a full scanline at a time unless you want to thrash your disk system
re-reading them repeatedly to pull one line of data out of each tile and
piece them together to make a scanline each time. Alternately, if the tiles
contain a multiple of 8 bits, you could just swap the top left tile with
the bottom right one while reversing the bits. For lines that are not a 
multiple of 8 bits, you will have to "borrow and carry" them across tiles.

My code is intended for processing a series of two or three hundred smaller 
images, say 2600x4200, or ten or twenty 14400x10800 pixel images in a 
single file so it makes extensive use of the same buffers rather than 
allocating a buffer for each image.

Richard Nolde