mirror of
https://github.com/gnustep/libs-gui.git
synced 2025-04-22 07:10:46 +00:00
16bit (#123)
* Fix compiler warnings * Attempt to sort out byte order for 15 bit images. * Try to get integer types from standard location * Remove extra swap code by using more complex condition. Thanks to Riccardo Mottola.
This commit is contained in:
parent
6ecfa261f6
commit
a047b10a51
6 changed files with 163 additions and 79 deletions
|
@ -27,7 +27,8 @@
|
|||
#import <Foundation/Foundation.h>
|
||||
#import <AppKit/AppKit.h>
|
||||
|
||||
@interface GSNamedColorPicker: NSColorPicker <NSColorPickingCustom, NSTextFieldDelegate>
|
||||
@interface GSNamedColorPicker: NSColorPicker <NSColorPickingCustom, NSTextFieldDelegate,
|
||||
NSComboBoxDataSource>
|
||||
{
|
||||
NSView *baseView;
|
||||
NSComboBox *cb;
|
||||
|
|
|
@ -90,7 +90,24 @@ typedef enum _NSBitmapFormat
|
|||
{
|
||||
NSAlphaFirstBitmapFormat = 1,
|
||||
NSAlphaNonpremultipliedBitmapFormat = 2,
|
||||
NSFloatingPointSamplesBitmapFormat = 4
|
||||
NSFloatingPointSamplesBitmapFormat = 4,
|
||||
|
||||
#if OS_API_VERSION(MAC_OS_X_VERSION_10_5, MAC_OS_X_VERSION_10_14)
|
||||
NS16BitLittleEndianBitmapFormat = (1 << 8),
|
||||
NS32BitLittleEndianBitmapFormat = (1 << 9),
|
||||
NS16BitBigEndianBitmapFormat = (1 << 10),
|
||||
NS32BitBigEndianBitmapFormat = (1 << 11),
|
||||
#endif
|
||||
|
||||
#if OS_API_VERSION(MAC_OS_X_VERSION_10_12, GS_API_LATEST)
|
||||
NSBitmapFormatAlphaFirst = 1,
|
||||
NSBitmapFormatAlphaNonpremultiplied = (1 << 1),
|
||||
NSBitmapFormatFloatingPointSamples = (1 << 2),
|
||||
NSBitmapFormatSixteenBitLittleEndian = (1 << 8),
|
||||
NSBitmapFormatThirtyTwoBitLittleEndian = (1 << 9),
|
||||
NSBitmapFormatSixteenBitBigEndian = (1 << 10),
|
||||
NSBitmapFormatThirtyTwoBitBigEndian = (1 << 11)
|
||||
#endif
|
||||
} NSBitmapFormat;
|
||||
|
||||
typedef enum _NSImageRepLoadStatus
|
||||
|
|
|
@ -106,6 +106,7 @@ static void reader_func(png_structp png_struct, png_bytep data,
|
|||
BOOL alpha;
|
||||
int bpp;
|
||||
NSString *colorspace;
|
||||
NSBitmapFormat bitmapFormat = NSAlphaNonpremultipliedBitmapFormat;
|
||||
|
||||
reader_struct_t reader;
|
||||
|
||||
|
@ -228,6 +229,15 @@ static void reader_func(png_structp png_struct, png_bytep data,
|
|||
png_read_image(png_struct, row_pointers);
|
||||
}
|
||||
|
||||
if (depth == 16)
|
||||
{
|
||||
bitmapFormat |= NSBitmapFormatSixteenBitBigEndian;
|
||||
}
|
||||
else if (depth == 32)
|
||||
{
|
||||
bitmapFormat |= NSBitmapFormatThirtyTwoBitBigEndian;
|
||||
}
|
||||
|
||||
self = [self initWithBitmapDataPlanes: &buf
|
||||
pixelsWide: width
|
||||
pixelsHigh: height
|
||||
|
@ -236,7 +246,7 @@ static void reader_func(png_structp png_struct, png_bytep data,
|
|||
hasAlpha: alpha
|
||||
isPlanar: NO
|
||||
colorSpaceName: colorspace
|
||||
bitmapFormat: NSAlphaNonpremultipliedBitmapFormat
|
||||
bitmapFormat: bitmapFormat
|
||||
bytesPerRow: bytes_per_row
|
||||
bitsPerPixel: bpp];
|
||||
|
||||
|
|
|
@ -670,33 +670,62 @@
|
|||
* this is strictly necessary for OpenStep tiffs.
|
||||
*/
|
||||
static unsigned int
|
||||
_get_bit_value(unsigned char *base, long msb_off, int bit_width)
|
||||
_get_bit_value(unsigned char *base, long msb_off, int bit_width,
|
||||
NSBitmapFormat format)
|
||||
{
|
||||
long lsb_off, byte1, byte2;
|
||||
int shift, value;
|
||||
if (bit_width == 16)
|
||||
{
|
||||
long byte1 = msb_off / 8;
|
||||
long byte2 = byte1 + 1;
|
||||
uint16_t value;
|
||||
|
||||
/*
|
||||
* Firstly we calculate the position of the msb and lsb in terms
|
||||
* of bit offsets and thus byte offsets. The shift is the number of
|
||||
* spare bits left in the byte containing the lsb
|
||||
*/
|
||||
lsb_off= msb_off+bit_width-1;
|
||||
byte1= msb_off/8;
|
||||
byte2= lsb_off/8;
|
||||
shift= 7-(lsb_off%8);
|
||||
if ((NSHostByteOrder() == NS_BigEndian && !(format & NSBitmapFormatSixteenBitLittleEndian)) ||
|
||||
(NSHostByteOrder() == NS_LittleEndian && (format & NSBitmapFormatSixteenBitBigEndian)))
|
||||
{
|
||||
value = base[byte2] | base[byte1] << 8;
|
||||
}
|
||||
else
|
||||
{
|
||||
value = base[byte1] | base[byte2] << 8;
|
||||
}
|
||||
|
||||
/*
|
||||
* We now get the value from the byte array, possibly using two bytes if
|
||||
* the required set of bits crosses the byte boundary. This is then shifted
|
||||
* down to it's correct position and extraneous bits masked off before
|
||||
* being returned.
|
||||
*/
|
||||
value=base[byte2];
|
||||
if (byte1!=byte2)
|
||||
value|= base[byte1]<<8;
|
||||
value >>= shift;
|
||||
return value;
|
||||
}
|
||||
else if (bit_width == 32)
|
||||
{
|
||||
// FIXME Currently not handled
|
||||
return 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
long lsb_off, byte1, byte2;
|
||||
unsigned int shift, value;
|
||||
|
||||
return value & ((1<<bit_width)-1);
|
||||
/*
|
||||
* Firstly we calculate the position of the msb and lsb in terms
|
||||
* of bit offsets and thus byte offsets. The shift is the number of
|
||||
* spare bits left in the byte containing the lsb
|
||||
*/
|
||||
lsb_off = msb_off + bit_width - 1;
|
||||
byte1 = msb_off / 8;
|
||||
byte2 = lsb_off / 8;
|
||||
shift = 7 - (lsb_off % 8);
|
||||
|
||||
/*
|
||||
* We now get the value from the byte array, possibly using two bytes if
|
||||
* the required set of bits crosses the byte boundary. This is then shifted
|
||||
* down to it's correct position and extraneous bits masked off before
|
||||
* being returned.
|
||||
*/
|
||||
value = base[byte2];
|
||||
if (byte1 != byte2)
|
||||
{
|
||||
value |= base[byte1] << 8;
|
||||
}
|
||||
value >>= shift;
|
||||
|
||||
return value & ((1 << bit_width) - 1);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -732,7 +761,7 @@ _get_bit_value(unsigned char *base, long msb_off, int bit_width)
|
|||
for (i = 0; i < _numColors; i++)
|
||||
{
|
||||
pixelData[i] = _get_bit_value(_imagePlanes[i] + line_offset,
|
||||
offset, _bitsPerSample);
|
||||
offset, _bitsPerSample, _format);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -752,7 +781,7 @@ _get_bit_value(unsigned char *base, long msb_off, int bit_width)
|
|||
for (i = 0; i < _numColors; i++)
|
||||
{
|
||||
pixelData[i] = _get_bit_value(_imagePlanes[0] + line_offset,
|
||||
offset, _bitsPerSample);
|
||||
offset, _bitsPerSample, _format);
|
||||
offset += _bitsPerSample;
|
||||
}
|
||||
}
|
||||
|
@ -761,35 +790,62 @@ _get_bit_value(unsigned char *base, long msb_off, int bit_width)
|
|||
|
||||
static void
|
||||
_set_bit_value(unsigned char *base, long msb_off, int bit_width,
|
||||
unsigned int value)
|
||||
NSBitmapFormat format, unsigned int value)
|
||||
{
|
||||
long lsb_off, byte1, byte2;
|
||||
int shift;
|
||||
int all;
|
||||
if (bit_width == 16)
|
||||
{
|
||||
long byte1 = msb_off / 8;
|
||||
long byte2 = byte1 + 1;
|
||||
uint16_t value16 = value;
|
||||
|
||||
/*
|
||||
* Firstly we calculate the position of the msb and lsb in terms
|
||||
* of bit offsets and thus byte offsets. The shift is the number of
|
||||
* spare bits left in the byte containing the lsb
|
||||
*/
|
||||
lsb_off= msb_off+bit_width-1;
|
||||
byte1= msb_off/8;
|
||||
byte2= lsb_off/8;
|
||||
shift= 7-(lsb_off%8);
|
||||
if ((NSHostByteOrder() == NS_BigEndian && !(format & NSBitmapFormatSixteenBitLittleEndian)) ||
|
||||
(NSHostByteOrder() == NS_LittleEndian && (format & NSBitmapFormatSixteenBitBigEndian)))
|
||||
{
|
||||
base[byte1] = (value16 >> 8);
|
||||
base[byte2] = (value16 & 255);
|
||||
}
|
||||
else
|
||||
{
|
||||
base[byte2] = (value16 >> 8);
|
||||
base[byte1] = (value16 & 255);
|
||||
}
|
||||
}
|
||||
else if (bit_width == 32)
|
||||
{
|
||||
// FIXME Currently not handled
|
||||
}
|
||||
else
|
||||
{
|
||||
long lsb_off, byte1, byte2;
|
||||
int shift;
|
||||
int all;
|
||||
|
||||
/*
|
||||
* We now set the value in the byte array, possibly using two bytes if
|
||||
* the required set of bits crosses the byte boundary. This value is
|
||||
* first shifted up to it's correct position and extraneous bits are
|
||||
* masked off.
|
||||
*/
|
||||
value &= ((1<<bit_width)-1);
|
||||
value <<= shift;
|
||||
all = ((1<<bit_width)-1) << shift;
|
||||
/*
|
||||
* Firstly we calculate the position of the msb and lsb in terms
|
||||
* of bit offsets and thus byte offsets. The shift is the number of
|
||||
* spare bits left in the byte containing the lsb
|
||||
*/
|
||||
lsb_off = msb_off + bit_width - 1;
|
||||
byte1 = msb_off / 8;
|
||||
byte2 = lsb_off/ 8;
|
||||
shift = 7 - (lsb_off % 8);
|
||||
|
||||
if (byte1 != byte2)
|
||||
base[byte1] = (value >> 8) | (base[byte1] & ~(all >> 8));
|
||||
base[byte2] = (value & 255) | (base[byte2] & ~(all & 255));
|
||||
/*
|
||||
* We now set the value in the byte array, possibly using two bytes if
|
||||
* the required set of bits crosses the byte boundary. This value is
|
||||
* first shifted up to it's correct position and extraneous bits are
|
||||
* masked off.
|
||||
*/
|
||||
value &= ((1 << bit_width) - 1);
|
||||
value <<= shift;
|
||||
all = ((1 << bit_width) - 1) << shift;
|
||||
|
||||
if (byte1 != byte2)
|
||||
{
|
||||
base[byte1] = (value >> 8) | (base[byte1] & ~(all >> 8));
|
||||
}
|
||||
base[byte2] = (value & 255) | (base[byte2] & ~(all & 255));
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -831,7 +887,7 @@ _set_bit_value(unsigned char *base, long msb_off, int bit_width,
|
|||
for (i = 0; i < _numColors; i++)
|
||||
{
|
||||
_set_bit_value(_imagePlanes[i] + line_offset,
|
||||
offset, _bitsPerSample, pixelData[i]);
|
||||
offset, _bitsPerSample, _format, pixelData[i]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -851,7 +907,7 @@ _set_bit_value(unsigned char *base, long msb_off, int bit_width,
|
|||
for (i = 0; i < _numColors; i++)
|
||||
{
|
||||
_set_bit_value(_imagePlanes[0] + line_offset,
|
||||
offset, _bitsPerSample, pixelData[i]);
|
||||
offset, _bitsPerSample, _format, pixelData[i]);
|
||||
offset += _bitsPerSample;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -37,21 +37,21 @@
|
|||
#define _GNUstep_H_tiff
|
||||
|
||||
#include <tiffio.h>
|
||||
#include <sys/types.h>
|
||||
#include <inttypes.h>
|
||||
|
||||
/* Structure to store common information about a tiff. */
|
||||
typedef struct {
|
||||
uint16 numImages; /* number of images in tiff */
|
||||
uint16 imageNumber; /* number of current image */
|
||||
uint32 subfileType;
|
||||
uint32 width;
|
||||
uint32 height;
|
||||
uint16 bitsPerSample; /* number of bits per data channel */
|
||||
uint16 samplesPerPixel; /* number of channels per pixel */
|
||||
uint16 planarConfig; /* meshed or separate */
|
||||
uint16 photoInterp; /* photometric interpretation of bitmap data, */
|
||||
uint16 compression;
|
||||
uint16 extraSamples; /* Alpha */
|
||||
uint16_t numImages; /* number of images in tiff */
|
||||
uint16_t imageNumber; /* number of current image */
|
||||
uint32_t subfileType;
|
||||
uint32_t width;
|
||||
uint32_t height;
|
||||
uint16_t bitsPerSample; /* number of bits per data channel */
|
||||
uint16_t samplesPerPixel; /* number of channels per pixel */
|
||||
uint16_t planarConfig; /* meshed or separate */
|
||||
uint16_t photoInterp; /* photometric interpretation of bitmap data, */
|
||||
uint16_t compression;
|
||||
uint16_t extraSamples; /* Alpha */
|
||||
int assocAlpha;
|
||||
int quality; /* compression quality (for jpeg) 1 to 255 */
|
||||
int error;
|
||||
|
@ -60,10 +60,10 @@ typedef struct {
|
|||
} NSTiffInfo;
|
||||
|
||||
typedef struct {
|
||||
uint32 size;
|
||||
uint16 *red;
|
||||
uint16 *green;
|
||||
uint16 *blue;
|
||||
uint32_t size;
|
||||
uint16_t *red;
|
||||
uint16_t *green;
|
||||
uint16_t *blue;
|
||||
} NSTiffColormap;
|
||||
|
||||
typedef char* realloc_data_callback(char* data, long size);
|
||||
|
|
|
@ -271,7 +271,7 @@ NSTiffInfo *
|
|||
NSTiffGetInfo(int imageNumber, TIFF* image)
|
||||
{
|
||||
NSTiffInfo* info;
|
||||
uint16 *sample_info = NULL;
|
||||
uint16_t *sample_info = NULL;
|
||||
|
||||
if (image == NULL)
|
||||
return NULL;
|
||||
|
@ -328,7 +328,7 @@ NSTiffGetInfo(int imageNumber, TIFF* image)
|
|||
}
|
||||
|
||||
{
|
||||
uint16 resolution_unit;
|
||||
uint16_t resolution_unit;
|
||||
float xres, yres;
|
||||
if (TIFFGetField(image, TIFFTAG_XRESOLUTION, &xres)
|
||||
&& TIFFGetField(image, TIFFTAG_YRESOLUTION, &yres))
|
||||
|
@ -369,9 +369,9 @@ NSTiffRead(TIFF *image, NSTiffInfo *info, unsigned char *data)
|
|||
int i;
|
||||
unsigned int row, col;
|
||||
int error = 0;
|
||||
uint8* outP;
|
||||
uint8* buf;
|
||||
uint8* raster;
|
||||
uint8_t* outP;
|
||||
uint8_t* buf;
|
||||
uint8_t* raster;
|
||||
NSTiffColormap* map;
|
||||
tmsize_t scan_line_size;
|
||||
|
||||
|
@ -389,7 +389,7 @@ NSTiffRead(TIFF *image, NSTiffInfo *info, unsigned char *data)
|
|||
scan_line_size = TIFFScanlineSize(image);
|
||||
buf = _TIFFmalloc(scan_line_size);
|
||||
|
||||
raster = (uint8 *)data;
|
||||
raster = (uint8_t *)data;
|
||||
outP = raster;
|
||||
switch (info->photoInterp)
|
||||
{
|
||||
|
@ -419,7 +419,7 @@ NSTiffRead(TIFF *image, NSTiffInfo *info, unsigned char *data)
|
|||
{
|
||||
for (row = 0; row < info->height; ++row)
|
||||
{
|
||||
uint8 *inP;
|
||||
uint8_t *inP;
|
||||
READ_SCANLINE(0);
|
||||
inP = buf;
|
||||
for (col = 0; col < info->width; col++)
|
||||
|
@ -474,7 +474,7 @@ int
|
|||
NSTiffWrite(TIFF *image, NSTiffInfo *info, unsigned char *data)
|
||||
{
|
||||
void* buf = (void*)data;
|
||||
uint16 sample_info[1];
|
||||
uint16_t sample_info[1];
|
||||
int i;
|
||||
unsigned int row;
|
||||
int error = 0;
|
||||
|
|
Loading…
Reference in a new issue