mirror of
https://github.com/gnustep/libs-gui.git
synced 2025-04-23 07:00:46 +00:00
try to swap 16bit and 32bit images line-per-line always into host byte order for TIFF library to write
This commit is contained in:
parent
82dce67eb4
commit
7c833cb5a6
3 changed files with 97 additions and 3 deletions
|
@ -39,6 +39,7 @@
|
|||
#import <Foundation/NSException.h>
|
||||
#import <Foundation/NSFileManager.h>
|
||||
#import <Foundation/NSValue.h>
|
||||
#import <Foundation/NSByteOrder.h>
|
||||
#import "AppKit/AppKitExceptions.h"
|
||||
#import "AppKit/NSGraphics.h"
|
||||
#import "AppKit/NSGraphicsContext.h"
|
||||
|
@ -1552,6 +1553,7 @@ _set_bit_value(unsigned char *base, long msb_off, int bit_width,
|
|||
[self _fillTIFFInfo: &info
|
||||
usingCompression: compression
|
||||
factor: factor];
|
||||
|
||||
if (NSTiffWrite(image, &info, [self bitmapData]) != 0)
|
||||
{
|
||||
[NSException raise: NSTIFFException format: @"Writing data"];
|
||||
|
@ -2125,6 +2127,8 @@ _set_bit_value(unsigned char *base, long msb_off, int bit_width,
|
|||
factor = 1;
|
||||
info->quality = factor * 100;
|
||||
info->error = 0;
|
||||
|
||||
info->bitmapFormat = (uint16_t)_format;
|
||||
}
|
||||
|
||||
- (void) _premultiply
|
||||
|
|
|
@ -57,6 +57,7 @@ typedef struct {
|
|||
int error;
|
||||
float xdpi;
|
||||
float ydpi;
|
||||
uint16_t bitmapFormat; /* NSBitmapFormat*/
|
||||
} NSTiffInfo;
|
||||
|
||||
typedef struct {
|
||||
|
|
|
@ -64,7 +64,9 @@
|
|||
#import <Foundation/NSString.h>
|
||||
#import <Foundation/NSDictionary.h>
|
||||
#import <Foundation/NSEnumerator.h>
|
||||
#import <Foundation/NSByteOrder.h>
|
||||
#import "GSGuiPrivate.h"
|
||||
#import <AppKit/NSBitmapImageRep.h>
|
||||
|
||||
#include <math.h>
|
||||
#include <stdlib.h>
|
||||
|
@ -465,20 +467,42 @@ NSTiffRead(TIFF *image, NSTiffInfo *info, unsigned char *data)
|
|||
}
|
||||
|
||||
#define WRITE_SCANLINE(sample) \
|
||||
if (TIFFWriteScanline(image, buf, row, sample) != 1) { \
|
||||
if (TIFFWriteScanline(image, bufSwap, row, sample) != 1) { \
|
||||
error = 1; \
|
||||
break; \
|
||||
}
|
||||
|
||||
#define SWAP16 \
|
||||
uint16_t *inBuf = (uint16_t*)buf; \
|
||||
uint16_t *outBuf = (uint16_t*)bufSwap; \
|
||||
unsigned swapSample; \
|
||||
for (swapSample = 0; swapSample < scan_line_size / 2; swapSample++) \
|
||||
{ \
|
||||
outBuf[swapSample] = GSSwapI16(inBuf[swapSample]); \
|
||||
}
|
||||
|
||||
#define SWAP32 \
|
||||
uint32_t *inBuf = (uint32_t*)buf; \
|
||||
uint32_t *outBuf = (uint32_t*)bufSwap; \
|
||||
unsigned swapSample; \
|
||||
for (swapSample = 0; swapSample < scan_line_size / 4; swapSample++) \
|
||||
{ \
|
||||
outBuf[swapSample] = GSSwapI32(inBuf[swapSample]); \
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
NSTiffWrite(TIFF *image, NSTiffInfo *info, unsigned char *data)
|
||||
{
|
||||
void* buf = (void*)data;
|
||||
void *bufSwap = nil;
|
||||
uint16_t sample_info[1];
|
||||
int i;
|
||||
unsigned int row;
|
||||
int error = 0;
|
||||
tmsize_t scan_line_size;
|
||||
BOOL swap16 = NO;
|
||||
BOOL swap32 = NO;
|
||||
|
||||
if (info->numImages > 1)
|
||||
{
|
||||
|
@ -512,6 +536,21 @@ NSTiffWrite(TIFF *image, NSTiffInfo *info, unsigned char *data)
|
|||
TIFFSetField(image, TIFFTAG_EXTRASAMPLES, info->extraSamples, sample_info);
|
||||
scan_line_size = TIFFScanlineSize(image);
|
||||
|
||||
// check if image endianness is different from Host
|
||||
if (((info->bitmapFormat & NSBitmapFormatSixteenBitBigEndian) != 0) != (NSHostByteOrder() == NS_BigEndian))
|
||||
{
|
||||
swap16 = YES;
|
||||
}
|
||||
else if (((info->bitmapFormat & NSBitmapFormatThirtyTwoBitBigEndian) != 0) != (NSHostByteOrder() == NS_BigEndian))
|
||||
{
|
||||
swap32 = YES;
|
||||
}
|
||||
|
||||
if (swap16 || swap32)
|
||||
{
|
||||
bufSwap = malloc(scan_line_size); // sizeof(unsigned char)
|
||||
}
|
||||
|
||||
switch (info->photoInterp)
|
||||
{
|
||||
case PHOTOMETRIC_MINISBLACK:
|
||||
|
@ -520,6 +559,18 @@ NSTiffWrite(TIFF *image, NSTiffInfo *info, unsigned char *data)
|
|||
{
|
||||
for (row = 0; row < info->height; ++row)
|
||||
{
|
||||
if (swap16)
|
||||
{
|
||||
SWAP16
|
||||
}
|
||||
else if (swap32)
|
||||
{
|
||||
SWAP32
|
||||
}
|
||||
else
|
||||
{
|
||||
bufSwap = buf;
|
||||
}
|
||||
WRITE_SCANLINE(0)
|
||||
buf += scan_line_size;
|
||||
}
|
||||
|
@ -530,6 +581,18 @@ NSTiffWrite(TIFF *image, NSTiffInfo *info, unsigned char *data)
|
|||
{
|
||||
for (row = 0; row < info->height; ++row)
|
||||
{
|
||||
if (swap16)
|
||||
{
|
||||
SWAP16
|
||||
}
|
||||
else if (swap32)
|
||||
{
|
||||
SWAP32
|
||||
}
|
||||
else
|
||||
{
|
||||
bufSwap = buf;
|
||||
}
|
||||
WRITE_SCANLINE(i)
|
||||
buf += scan_line_size;
|
||||
}
|
||||
|
@ -542,6 +605,18 @@ NSTiffWrite(TIFF *image, NSTiffInfo *info, unsigned char *data)
|
|||
{
|
||||
for (row = 0; row < info->height; ++row)
|
||||
{
|
||||
if (swap16)
|
||||
{
|
||||
SWAP16
|
||||
}
|
||||
else if (swap32)
|
||||
{
|
||||
SWAP32
|
||||
}
|
||||
else
|
||||
{
|
||||
bufSwap = buf;
|
||||
}
|
||||
WRITE_SCANLINE(0)
|
||||
buf += scan_line_size;
|
||||
}
|
||||
|
@ -552,6 +627,18 @@ NSTiffWrite(TIFF *image, NSTiffInfo *info, unsigned char *data)
|
|||
{
|
||||
for (row = 0; row < info->height; ++row)
|
||||
{
|
||||
if (swap16)
|
||||
{
|
||||
SWAP16
|
||||
}
|
||||
else if (swap32)
|
||||
{
|
||||
SWAP32
|
||||
}
|
||||
else
|
||||
{
|
||||
bufSwap = buf;
|
||||
}
|
||||
WRITE_SCANLINE(i)
|
||||
buf += scan_line_size;
|
||||
}
|
||||
|
@ -569,6 +656,10 @@ NSTiffWrite(TIFF *image, NSTiffInfo *info, unsigned char *data)
|
|||
// Write out the directory as there may be more images comming
|
||||
TIFFWriteDirectory(image);
|
||||
TIFFFlush(image);
|
||||
if (swap16 || swap32)
|
||||
{
|
||||
free(bufSwap);
|
||||
}
|
||||
|
||||
return error;
|
||||
}
|
||||
|
@ -684,5 +775,3 @@ int NSTiffIsCodecConfigured(unsigned int codec)
|
|||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
|
|
Loading…
Reference in a new issue