ultimately i would like to have a 2D array loaded from a black and white tiff file such as
bool image[width][length];
where true is pixel present and false is blank, or vice versa i don't care.
Modify some bits and write it back out to a tiff
I'm using libtiff and C++, i attached a sample tiff
Basically, i followed one of the examples. Just modified it to print the buffer to a output file and it the result is bizzare
This is what the output looks like
€ €T € €T € € € € € € € € € € € € € € € € € € € € € €
Looks like its still in some kind of compressed format.
I tried other examples on libtiff site, and some from stackoverflow and haven't got anything really working.
Any help would be very MUCH appreciated!!
#include <stdio.h>
#include <tiffio.h>
#include <memory>
#include <fstream>
#include <iostream>
#pragma comment(lib,"libtiff.lib")
int main(int argc, char *argv[])
{
TIFF *image;
uint16 photo, bps, spp, fillorder;
uint32 width;
tsize_t stripSize;
unsigned long imageOffset, result;
int stripMax, stripCount;
char *buffer, tempbyte;
unsigned long bufferSize, count;
// Open the TIFF image
if((image = TIFFOpen("test.tiff", "r")) == NULL)
{
std::cout << "Could not open incoming image\n" << std::endl;
system("Pause");
return (42);
}
int imageWidth, imageLength, tileWidth, tileLength;
TIFFGetField(image, TIFFTAG_IMAGEWIDTH, &imageWidth);
TIFFGetField(image, TIFFTAG_IMAGELENGTH, &imageLength);
TIFFGetField(image, TIFFTAG_TILEWIDTH, &tileWidth);
TIFFGetField(image, TIFFTAG_TILELENGTH, &tileLength);
std::cout << "Image Width: " << imageWidth << std::endl;
std::cout << "Image Height: " << imageLength << std::endl;
std::cout << "Tile Width : " << tileWidth << std::endl;
std::cout << "Tile Height : " << tileLength << std::endl;
// Check that it is of a type that we support
if((TIFFGetField(image, TIFFTAG_BITSPERSAMPLE, &bps) == 0) || (bps != 1))
{
fprintf(stderr, "Either undefined or unsupported number of bits per sample\n");
return(43);
}
if((TIFFGetField(image, TIFFTAG_SAMPLESPERPIXEL, &spp) == 0) || (spp != 1))
{
fprintf(stderr, "Either undefined or unsupported number of samples per pixel\n");
return(44);
}
// Read in the possibly multiple strips
stripSize = TIFFStripSize (image);
stripMax = TIFFNumberOfStrips (image);
imageOffset = 0;
bufferSize = TIFFNumberOfStrips (image) * stripSize;
if((buffer = (char *) malloc(bufferSize)) == NULL)
{
fprintf(stderr, "Could not allocate enough memory for the uncompressed image\n"); return(42);
}
for (stripCount = 0; stripCount < stripMax; stripCount++)
{
if((result = TIFFReadEncodedStrip (image, stripCount, buffer + imageOffset, stripSize)) == -1)
{
fprintf(stderr, "Read error on input strip number %d\n", stripCount);
return(45);
}
imageOffset += result;
}
std::cout << "strip count: " << stripMax << std::endl;
// Deal with photometric interpretations
if(TIFFGetField(image, TIFFTAG_PHOTOMETRIC, &photo) == 0)
{
fprintf(stderr, "Image has an undefined photometric interpretation\n");
return(46);
}
if(photo != PHOTOMETRIC_MINISWHITE)
{
// Flip bits
printf("Fixing the photometric interpretation\n");
for(count = 0; count < bufferSize; count++)
buffer[count] = ~buffer[count];
}
// Deal with fillorder
if(TIFFGetField(image, TIFFTAG_FILLORDER, &fillorder) == 0)
{
fprintf(stderr, "Image has an undefined fillorder\n");
// return(47);
}
if(fillorder != FILLORDER_MSB2LSB)
{ // We need to swap bits -- ABCDEFGH becomes HGFEDCBA
printf("Fixing the fillorder\n");
for(count = 0; count < bufferSize; count++)
{
tempbyte = 0;
if(buffer[count] & 128) tempbyte += 1;
if(buffer[count] & 64) tempbyte += 2;
if(buffer[count] & 32) tempbyte += 4;
if(buffer[count] & 16) tempbyte += 8;
if(buffer[count] & 8) tempbyte += 16;
if(buffer[count] & 4) tempbyte += 32;
if(buffer[count] & 2) tempbyte += 64;
if(buffer[count] & 1) tempbyte += 128;
buffer[count] = tempbyte;
}
}
// Do whatever it is we do with the buffer -- we dump it in hex
if(TIFFGetField(image, TIFFTAG_IMAGEWIDTH, &width) == 0)
{
fprintf(stderr, "Image does not define its width\n");
return(48);
}
std::fstream file("output.txt",std::ios_base::out);
for(int i = 0; i < bufferSize; ++ i)
{
file << buffer[i];
}
file.close();
std::cout << bufferSize << std::endl;
system("Pause");
return 0;
}