Clean up endian support for images based on new system defines
Remove deprecated image functions
This commit is contained in:
parent
1fa5677d44
commit
f48b492303
8 changed files with 150 additions and 207 deletions
|
@ -9,6 +9,8 @@
|
|||
|
||||
#if GFX_USE_GDISP && GDISP_NEED_IMAGE
|
||||
|
||||
#include "gdisp_image_support.h"
|
||||
|
||||
#if GDISP_NEED_IMAGE_NATIVE
|
||||
extern gdispImageError gdispImageOpen_NATIVE(gdispImage *img);
|
||||
extern void gdispImageClose_NATIVE(gdispImage *img);
|
||||
|
@ -90,39 +92,6 @@ static gdispImageHandlers ImageHandlers[] = {
|
|||
#endif
|
||||
};
|
||||
|
||||
gdispImageError
|
||||
DEPRECATED("Use gdispImageOpenGFile() instead")
|
||||
gdispImageOpen(gdispImage *img) {
|
||||
return gdispImageOpenGFile(img, img->f);
|
||||
}
|
||||
|
||||
#if GFILE_NEED_MEMFS
|
||||
bool_t
|
||||
DEPRECATED("Use gdispImageOpenMemory() instead")
|
||||
gdispImageSetMemoryReader(gdispImage *img, const void *memimage) {
|
||||
img->f = gfileOpenMemory((void *)memimage, "rb");
|
||||
return img->f != 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
#if defined(WIN32) || GFX_USE_OS_WIN32 || GFX_USE_OS_LINUX || GFX_USE_OS_OSX
|
||||
bool_t
|
||||
DEPRECATED("Use gdispImageOpenFile() instead")
|
||||
gdispImageSetFileReader(gdispImage *img, const char *filename) {
|
||||
img->f = gfileOpen(filename, "rb");
|
||||
return img->f != 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
#if GFILE_NEED_CHIBIOSFS && GFX_USE_OS_CHIBIOS
|
||||
bool_t
|
||||
DEPRECATED("Use gdispImageOpenBaseFileStream() instead")
|
||||
gdispImageSetBaseFileStreamReader(gdispImage *img, void *BaseFileStreamPtr) {
|
||||
img->f = gfileOpenBaseFileStream(BaseFileStreamPtr, "rb");
|
||||
return img->f != 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
void gdispImageInit(gdispImage *img) {
|
||||
img->type = GDISP_IMAGE_TYPE_UNKNOWN;
|
||||
}
|
||||
|
@ -222,4 +191,8 @@ void gdispImageFree(gdispImage *img, void *ptr, size_t sz) {
|
|||
#endif
|
||||
}
|
||||
|
||||
#if GFX_CPU_ENDIAN != GFX_CPU_ENDIAN_LITTLE && GFX_CPU_ENDIAN != GFX_CPU_ENDIAN_BIG
|
||||
const uint8_t gdispImageEndianArray[4] = { 1, 2, 3, 4 };
|
||||
#endif
|
||||
|
||||
#endif /* GFX_USE_GDISP && GDISP_NEED_IMAGE */
|
||||
|
|
|
@ -52,52 +52,6 @@ typedef uint16_t gdispImageFlags;
|
|||
#define GDISP_IMAGE_FLG_ANIMATED 0x0002 /* The image has animation */
|
||||
#define GDISP_IMAGE_FLG_MULTIPAGE 0x0004 /* The image has multiple pages */
|
||||
|
||||
struct gdispImageIO;
|
||||
|
||||
/**
|
||||
* @brief An image IO close function
|
||||
*
|
||||
* @param[in] pio Pointer to the io structure
|
||||
* @param[in] desc The descriptor. A filename or an image structure pointer.
|
||||
*
|
||||
*/
|
||||
typedef void (*gdispImageIOCloseFn)(struct gdispImageIO *pio);
|
||||
|
||||
/**
|
||||
* @brief An image IO read function
|
||||
* @returns The number of bytes actually read or 0 on error
|
||||
*
|
||||
* @param[in] pio Pointer to the io structure
|
||||
* @param[in] buf Where the results should be placed
|
||||
* @param[in] len The number of bytes to read
|
||||
*
|
||||
*/
|
||||
typedef size_t (*gdispImageIOReadFn)(struct gdispImageIO *pio, void *buf, size_t len);
|
||||
|
||||
/**
|
||||
* @brief An image IO seek function
|
||||
*
|
||||
* @param[in] pio Pointer to the io structure
|
||||
* @param[in] pos Which byte to seek to relative to the start of the "file".
|
||||
*
|
||||
*/
|
||||
typedef void (*gdispImageIOSeekFn)(struct gdispImageIO *pio, size_t pos);
|
||||
|
||||
typedef struct gdispImageIOFunctions {
|
||||
gdispImageIOReadFn read; /* @< The function to read input */
|
||||
gdispImageIOSeekFn seek; /* @< The function to seek input */
|
||||
gdispImageIOCloseFn close; /* @< The function to close input */
|
||||
} gdispImageIOFunctions;
|
||||
|
||||
/**
|
||||
* @brief The structure defining the IO routines for image handling
|
||||
*/
|
||||
typedef struct gdispImageIO {
|
||||
const void * fd; /* @< The "file" descriptor */
|
||||
size_t pos; /* @< The current "file" position */
|
||||
const gdispImageIOFunctions *fns; /* @< The current "file" functions */
|
||||
} gdispImageIO;
|
||||
|
||||
/**
|
||||
* @brief The structure for an image
|
||||
*/
|
||||
|
@ -119,19 +73,6 @@ typedef struct gdispImage {
|
|||
extern "C" {
|
||||
#endif
|
||||
|
||||
/*
|
||||
* Deprecated Functions.
|
||||
*/
|
||||
gdispImageError DEPRECATED("Use gdispImageOpenGFile() instead") gdispImageOpen(gdispImage *img);
|
||||
bool_t DEPRECATED("Use gdispImageOpenMemory() instead") gdispImageSetMemoryReader(gdispImage *img, const void *memimage);
|
||||
#if GFX_USE_OS_CHIBIOS
|
||||
bool_t DEPRECATED("Use gdispImageOpenBaseFileStream() instead") gdispImageSetBaseFileStreamReader(gdispImage *img, void *BaseFileStreamPtr);
|
||||
#endif
|
||||
#if defined(WIN32) || GFX_USE_OS_WIN32 || GFX_USE_OS_LINUX || GFX_USE_OS_OSX
|
||||
bool_t DEPRECATED("Please use gdispImageOpenFile() instead") gdispImageSetFileReader(gdispImage *img, const char *filename);
|
||||
#define gdispImageSetSimulFileReader(img, fname) gdispImageSetFileReader(img, fname)
|
||||
#endif
|
||||
|
||||
/**
|
||||
* @brief Initialise a gdispImage object
|
||||
*
|
||||
|
|
|
@ -9,11 +9,7 @@
|
|||
|
||||
#if GFX_USE_GDISP && GDISP_NEED_IMAGE && GDISP_NEED_IMAGE_BMP
|
||||
|
||||
/**
|
||||
* Helper Routines Needed
|
||||
*/
|
||||
void *gdispImageAlloc(gdispImage *img, size_t sz);
|
||||
void gdispImageFree(gdispImage *img, void *ptr, size_t sz);
|
||||
#include "gdisp_image_support.h"
|
||||
|
||||
/**
|
||||
* How big a pixel array to allocate for blitting (in pixels)
|
||||
|
@ -22,36 +18,6 @@ void gdispImageFree(gdispImage *img, void *ptr, size_t sz);
|
|||
*/
|
||||
#define BLIT_BUFFER_SIZE 32
|
||||
|
||||
/*
|
||||
* Determining endianness as at compile time is not guaranteed or compiler portable.
|
||||
* We use the best test we can. If we can't guarantee little endianness we do things the
|
||||
* hard way.
|
||||
*/
|
||||
#define GUARANTEED_LITTLE_ENDIAN (!defined(SAFE_ENDIAN) && !defined(SAFE_ALIGNMENT) && (\
|
||||
(defined(__BYTE_ORDER__)&&(__BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__)) \
|
||||
|| defined(__LITTLE_ENDIAN__) \
|
||||
|| defined(__LITTLE_ENDIAN) \
|
||||
|| defined(_LITTLE_ENDIAN) \
|
||||
/* || (1 == *(unsigned char *)&(const int){1})*/ \
|
||||
))
|
||||
|
||||
|
||||
/* This is a runtime test */
|
||||
static const uint8_t dwordOrder[4] = { 1, 2, 3, 4 };
|
||||
|
||||
#define isWordLittleEndian() (*(uint16_t *)&dwordOrder == 0x0201)
|
||||
#define isDWordLittleEndian() (*(uint32_t *)&dwordOrder == 0x04030201)
|
||||
|
||||
#if GUARANTEED_LITTLE_ENDIAN
|
||||
/* These are fast routines for guaranteed little endian machines */
|
||||
#define CONVERT_FROM_WORD_LE(w)
|
||||
#define CONVERT_FROM_DWORD_LE(dw)
|
||||
#else
|
||||
/* These are slower routines for when little endianness cannot be guaranteed at compile time */
|
||||
#define CONVERT_FROM_WORD_LE(w) { if (!isWordLittleEndian()) w = ((((uint16_t)(w))>>8)|(((uint16_t)(w))<<8)); }
|
||||
#define CONVERT_FROM_DWORD_LE(dw) { if (!isDWordLittleEndian()) dw = (((uint32_t)(((const uint8_t *)(&dw))[0]))|(((uint32_t)(((const uint8_t *)(&dw))[1]))<<8)|(((uint32_t)(((const uint8_t *)(&dw))[2]))<<16)|(((uint32_t)(((const uint8_t *)(&dw))[3]))<<24)); }
|
||||
#endif
|
||||
|
||||
typedef struct gdispImagePrivate {
|
||||
uint8_t bmpflags;
|
||||
#define BMP_V2 0x01 // Version 2 (old) header format
|
||||
|
@ -141,14 +107,14 @@ gdispImageError gdispImageOpen_BMP(gdispImage *img) {
|
|||
/* Get the offset to the bitmap data */
|
||||
if (gfileRead(img->f, &priv->frame0pos, 4) != 4)
|
||||
goto baddatacleanup;
|
||||
CONVERT_FROM_DWORD_LE(priv->frame0pos);
|
||||
gdispImageMakeLE32(priv->frame0pos);
|
||||
|
||||
/* Process the BITMAPCOREHEADER structure */
|
||||
|
||||
/* Get the offset to the colour data */
|
||||
if (gfileRead(img->f, &offsetColorTable, 4) != 4)
|
||||
goto baddatacleanup;
|
||||
CONVERT_FROM_DWORD_LE(offsetColorTable);
|
||||
gdispImageMakeLE32(offsetColorTable);
|
||||
offsetColorTable += 14; // Add the size of the BITMAPFILEHEADER
|
||||
|
||||
// Detect our bitmap version
|
||||
|
@ -159,23 +125,19 @@ gdispImageError gdispImageOpen_BMP(gdispImage *img) {
|
|||
if (gfileRead(img->f, priv->buf, 12-4) != 12-4)
|
||||
goto baddatacleanup;
|
||||
// Get the width
|
||||
img->width = *(uint16_t *)(((uint8_t *)priv->buf)+0);
|
||||
CONVERT_FROM_WORD_LE(img->width);
|
||||
img->width = gdispImageGetAlignedLE16(priv->buf, 0);
|
||||
// Get the height
|
||||
img->height = *(uint16_t *)(((uint8_t *)priv->buf)+2);
|
||||
CONVERT_FROM_WORD_LE(img->height);
|
||||
img->height = gdispImageGetAlignedLE16(priv->buf, 2);
|
||||
if (img->height < 0) {
|
||||
img->priv->bmpflags |= BMP_TOP_TO_BOTTOM;
|
||||
img->height = -img->height;
|
||||
}
|
||||
// Get the planes
|
||||
aword = *(uint16_t *)(((uint8_t *)priv->buf)+4);
|
||||
CONVERT_FROM_WORD_LE(aword);
|
||||
aword = gdispImageGetAlignedLE16(priv->buf, 4);
|
||||
if (aword != 1)
|
||||
goto unsupportedcleanup;
|
||||
// Get the bits per pixel
|
||||
aword = *(uint16_t *)(((uint8_t *)priv->buf)+6);
|
||||
CONVERT_FROM_WORD_LE(aword);
|
||||
aword = gdispImageGetAlignedLE16(priv->buf, 6);
|
||||
switch(aword) {
|
||||
#if GDISP_NEED_IMAGE_BMP_1
|
||||
case 1:
|
||||
|
@ -208,14 +170,12 @@ gdispImageError gdispImageOpen_BMP(gdispImage *img) {
|
|||
if (gfileRead(img->f, priv->buf, 40-4) != 40-4)
|
||||
goto baddatacleanup;
|
||||
// Get the width
|
||||
adword = *(uint32_t *)(((uint8_t *)priv->buf)+0);
|
||||
CONVERT_FROM_DWORD_LE(adword);
|
||||
adword = gdispImageGetAlignedLE32(priv->buf, 0);
|
||||
if (adword > 32768) // This also picks up negative values
|
||||
goto unsupportedcleanup;
|
||||
img->width = adword;
|
||||
// Get the height
|
||||
adword = *(uint32_t *)(((uint8_t *)priv->buf)+4);
|
||||
CONVERT_FROM_DWORD_LE(adword);
|
||||
adword = gdispImageGetAlignedLE32(priv->buf, 4);
|
||||
if ((int32_t)adword < 0) { // Negative test
|
||||
priv->bmpflags |= BMP_TOP_TO_BOTTOM;
|
||||
adword = -adword;
|
||||
|
@ -224,13 +184,11 @@ gdispImageError gdispImageOpen_BMP(gdispImage *img) {
|
|||
goto unsupportedcleanup;
|
||||
img->height = adword;
|
||||
// Get the planes
|
||||
aword = *(uint16_t *)(((uint8_t *)priv->buf)+8);
|
||||
CONVERT_FROM_WORD_LE(aword);
|
||||
aword = gdispImageGetAlignedLE16(priv->buf, 8);
|
||||
if (aword != 1)
|
||||
goto unsupportedcleanup;
|
||||
// Get the bits per pixel
|
||||
aword = *(uint16_t *)(((uint8_t *)priv->buf)+10);
|
||||
CONVERT_FROM_WORD_LE(aword);
|
||||
aword = gdispImageGetAlignedLE16(priv->buf, 10);
|
||||
switch(aword) {
|
||||
#if GDISP_NEED_IMAGE_BMP_1
|
||||
case 1:
|
||||
|
@ -263,8 +221,7 @@ gdispImageError gdispImageOpen_BMP(gdispImage *img) {
|
|||
}
|
||||
priv->bitsperpixel = aword;
|
||||
// Get the compression
|
||||
adword = *(uint32_t *)(((uint8_t *)priv->buf)+12);
|
||||
CONVERT_FROM_DWORD_LE(adword);
|
||||
adword = gdispImageGetAlignedLE32(priv->buf, 12);
|
||||
switch(adword) {
|
||||
case 0: // BI_RGB - uncompressed
|
||||
break;
|
||||
|
@ -297,8 +254,7 @@ gdispImageError gdispImageOpen_BMP(gdispImage *img) {
|
|||
priv->bitsperpixel = aword;
|
||||
#if GDISP_NEED_IMAGE_BMP_1 || GDISP_NEED_IMAGE_BMP_4 || GDISP_NEED_IMAGE_BMP_4_RLE || GDISP_NEED_IMAGE_BMP_8 || GDISP_NEED_IMAGE_BMP_8_RLE
|
||||
// Get the actual colors used
|
||||
adword = *(uint32_t *)(((uint8_t *)priv->buf)+28);
|
||||
CONVERT_FROM_DWORD_LE(adword);
|
||||
adword = gdispImageGetAlignedLE32(priv->buf, 28);
|
||||
if (adword && adword < priv->palsize)
|
||||
priv->palsize = adword;
|
||||
#endif
|
||||
|
@ -332,14 +288,14 @@ gdispImageError gdispImageOpen_BMP(gdispImage *img) {
|
|||
if (priv->bmpflags & BMP_COMP_MASK) {
|
||||
gfileSetPos(img->f, offsetColorTable);
|
||||
if (gfileRead(img->f, &priv->maskred, 4) != 4) goto baddatacleanup;
|
||||
CONVERT_FROM_DWORD_LE(priv->maskred);
|
||||
gdispImageMakeLE32(priv->maskred);
|
||||
if (gfileRead(img->f, &priv->maskgreen, 4) != 4) goto baddatacleanup;
|
||||
CONVERT_FROM_DWORD_LE(priv->maskgreen);
|
||||
gdispImageMakeLE32(priv->maskgreen);
|
||||
if (gfileRead(img->f, &priv->maskblue, 4) != 4) goto baddatacleanup;
|
||||
CONVERT_FROM_DWORD_LE(priv->maskblue);
|
||||
gdispImageMakeLE32(priv->maskblue);
|
||||
if (priv->bmpflags & BMP_V4) {
|
||||
if (gfileRead(img->f, &priv->maskalpha, 4) != 4) goto baddatacleanup;
|
||||
CONVERT_FROM_DWORD_LE(priv->maskalpha);
|
||||
gdispImageMakeLE32(priv->maskalpha);
|
||||
} else
|
||||
priv->maskalpha = 0;
|
||||
} else if (priv->bitsperpixel == 16) {
|
||||
|
@ -644,8 +600,8 @@ static coord_t getPixels(gdispImage *img, coord_t x) {
|
|||
while(x < img->width && len <= BLIT_BUFFER_SIZE-2) {
|
||||
if (gfileRead(img->f, &w, 4) != 4)
|
||||
return 0;
|
||||
CONVERT_FROM_WORD_LE(w[0]);
|
||||
CONVERT_FROM_WORD_LE(w[1]);
|
||||
gdispImageMakeLE16(w[0]);
|
||||
gdispImageMakeLE16(w[1]);
|
||||
if (priv->shiftred < 0)
|
||||
r = (color_t)((w[0] & priv->maskred) << -priv->shiftred);
|
||||
else
|
||||
|
@ -712,7 +668,7 @@ static coord_t getPixels(gdispImage *img, coord_t x) {
|
|||
while(x < img->width && len < BLIT_BUFFER_SIZE) {
|
||||
if (gfileRead(img->f, &dw, 4) != 4)
|
||||
return 0;
|
||||
CONVERT_FROM_DWORD_LE(dw);
|
||||
gdispImageMakeLE32(dw);
|
||||
if (priv->shiftred < 0)
|
||||
r = (color_t)((dw & priv->maskred) << -priv->shiftred);
|
||||
else
|
||||
|
|
|
@ -9,11 +9,7 @@
|
|||
|
||||
#if GFX_USE_GDISP && GDISP_NEED_IMAGE && GDISP_NEED_IMAGE_GIF
|
||||
|
||||
/**
|
||||
* Helper Routines Needed
|
||||
*/
|
||||
void *gdispImageAlloc(gdispImage *img, size_t sz);
|
||||
void gdispImageFree(gdispImage *img, void *ptr, size_t sz);
|
||||
#include "gdisp_image_support.h"
|
||||
|
||||
/**
|
||||
* How big an array to allocate for blitting (in pixels)
|
||||
|
@ -21,36 +17,6 @@ void gdispImageFree(gdispImage *img, void *ptr, size_t sz);
|
|||
*/
|
||||
#define BLIT_BUFFER_SIZE 32
|
||||
|
||||
/*
|
||||
* Determining endianness as at compile time is not guaranteed or compiler portable.
|
||||
* We use the best test we can. If we can't guarantee little endianness we do things the
|
||||
* hard way.
|
||||
*/
|
||||
#define GUARANTEED_LITTLE_ENDIAN (!defined(SAFE_ENDIAN) && !defined(SAFE_ALIGNMENT) && (\
|
||||
(defined(__BYTE_ORDER__)&&(__BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__)) \
|
||||
|| defined(__LITTLE_ENDIAN__) \
|
||||
|| defined(__LITTLE_ENDIAN) \
|
||||
|| defined(_LITTLE_ENDIAN) \
|
||||
/* || (1 == *(unsigned char *)&(const int){1})*/ \
|
||||
))
|
||||
|
||||
|
||||
/* This is a runtime test */
|
||||
static const uint8_t dwordOrder[4] = { 1, 2, 3, 4 };
|
||||
|
||||
#define isWordLittleEndian() (*(uint16_t *)&dwordOrder == 0x0201)
|
||||
#define isDWordLittleEndian() (*(uint32_t *)&dwordOrder == 0x04030201)
|
||||
|
||||
#if GUARANTEED_LITTLE_ENDIAN
|
||||
/* These are fast routines for guaranteed little endian machines */
|
||||
#define CONVERT_FROM_WORD_LE(w)
|
||||
#define CONVERT_FROM_DWORD_LE(dw)
|
||||
#else
|
||||
/* These are slower routines for when little endianness cannot be guaranteed at compile time */
|
||||
#define CONVERT_FROM_WORD_LE(w) { if (!isWordLittleEndian()) w = ((((uint16_t)(w))>>8)|(((uint16_t)(w))<<8)); }
|
||||
#define CONVERT_FROM_DWORD_LE(dw) { if (!isDWordLittleEndian()) dw = (((uint32_t)(((const uint8_t *)(&dw))[0]))|(((uint32_t)(((const uint8_t *)(&dw))[1]))<<8)|(((uint32_t)(((const uint8_t *)(&dw))[2]))<<16)|(((uint32_t)(((const uint8_t *)(&dw))[3]))<<24)); }
|
||||
#endif
|
||||
|
||||
// We need a special error to indicate the end of file (which may not actually be an error)
|
||||
#define GDISP_IMAGE_EOF ((gdispImageError)-1)
|
||||
#define GDISP_IMAGE_LOOP ((gdispImageError)-2)
|
||||
|
@ -416,14 +382,10 @@ static gdispImageError initFrame(gdispImage *img) {
|
|||
// Read the Image Descriptor
|
||||
if (gfileRead(img->f, priv->buf, 9) != 9)
|
||||
return GDISP_IMAGE_ERR_BADDATA;
|
||||
priv->frame.x = *(uint16_t *)(((uint8_t *)priv->buf)+0);
|
||||
CONVERT_FROM_WORD_LE(priv->frame.x);
|
||||
priv->frame.y = *(uint16_t *)(((uint8_t *)priv->buf)+2);
|
||||
CONVERT_FROM_WORD_LE(priv->frame.y);
|
||||
priv->frame.width = *(uint16_t *)(((uint8_t *)priv->buf)+4);
|
||||
CONVERT_FROM_WORD_LE(priv->frame.width);
|
||||
priv->frame.height = *(uint16_t *)(((uint8_t *)priv->buf)+6);
|
||||
CONVERT_FROM_WORD_LE(priv->frame.height);
|
||||
priv->frame.x = gdispImageGetAlignedLE16(priv->buf, 0);
|
||||
priv->frame.y = gdispImageGetAlignedLE16(priv->buf, 2);
|
||||
priv->frame.width = gdispImageGetAlignedLE16(priv->buf, 4);
|
||||
priv->frame.height = gdispImageGetAlignedLE16(priv->buf, 6);
|
||||
if (((uint8_t *)priv->buf)[8] & 0x80) // Local color table?
|
||||
priv->frame.palsize = 2 << (((uint8_t *)priv->buf)[8] & 0x07);
|
||||
if (((uint8_t *)priv->buf)[8] & 0x40) // Interlaced?
|
||||
|
@ -468,8 +430,7 @@ static gdispImageError initFrame(gdispImage *img) {
|
|||
else
|
||||
img->flags &= ~GDISP_IMAGE_FLG_MULTIPAGE;
|
||||
// Process frame delay and the transparent color (if any)
|
||||
priv->frame.delay = *(uint16_t *)(((uint8_t *)priv->buf)+2);
|
||||
CONVERT_FROM_WORD_LE(priv->frame.delay);
|
||||
priv->frame.delay = gdispImageGetAlignedLE16(priv->buf, 2);
|
||||
priv->frame.paltrans = ((uint8_t *)priv->buf)[4];
|
||||
break;
|
||||
|
||||
|
@ -489,8 +450,7 @@ static gdispImageError initFrame(gdispImage *img) {
|
|||
&& ((uint8_t *)priv->buf)[7] == 'P' && ((uint8_t *)priv->buf)[8] == 'E' && ((uint8_t *)priv->buf)[9] == '2'
|
||||
&& ((uint8_t *)priv->buf)[10] == '.' && ((uint8_t *)priv->buf)[11] == '0') {
|
||||
if (((uint8_t *)priv->buf)[13] == 1) {
|
||||
priv->loops = *(uint16_t *)(((uint8_t *)priv->buf)+14);
|
||||
CONVERT_FROM_WORD_LE(priv->loops);
|
||||
priv->loops = gdispImageGetAlignedLE16(priv->buf, 14);
|
||||
priv->flags |= GIF_LOOP;
|
||||
if (!priv->loops)
|
||||
priv->flags |= GIF_LOOPFOREVER;
|
||||
|
@ -597,11 +557,9 @@ gdispImageError gdispImageOpen_GIF(gdispImage *img) {
|
|||
if (gfileRead(img->f, priv->buf, 7) != 7)
|
||||
goto baddatacleanup;
|
||||
// Get the width
|
||||
img->width = *(uint16_t *)(((uint8_t *)priv->buf)+0);
|
||||
CONVERT_FROM_WORD_LE(img->width);
|
||||
img->width = gdispImageGetAlignedLE16(priv->buf, 0);
|
||||
// Get the height
|
||||
img->height = *(uint16_t *)(((uint8_t *)priv->buf)+2);
|
||||
CONVERT_FROM_WORD_LE(img->height);
|
||||
img->height = gdispImageGetAlignedLE16(priv->buf, 2);
|
||||
if (((uint8_t *)priv->buf)[4] & 0x80) {
|
||||
// Global color table
|
||||
priv->palsize = 2 << (((uint8_t *)priv->buf)[4] & 0x07);
|
||||
|
|
|
@ -9,6 +9,8 @@
|
|||
|
||||
#if GFX_USE_GDISP && GDISP_NEED_IMAGE && GDISP_NEED_IMAGE_JPG
|
||||
|
||||
#include "gdisp_image_support.h"
|
||||
|
||||
#error "JPG support not implemented yet"
|
||||
|
||||
#endif /* GFX_USE_GDISP && GDISP_NEED_IMAGE && GDISP_NEED_IMAGE_JPG */
|
||||
|
|
|
@ -9,6 +9,8 @@
|
|||
|
||||
#if GFX_USE_GDISP && GDISP_NEED_IMAGE && GDISP_NEED_IMAGE_NATIVE
|
||||
|
||||
#include "gdisp_image_support.h"
|
||||
|
||||
/**
|
||||
* How big a pixel array to allocate for blitting
|
||||
* Bigger is faster but uses more RAM.
|
||||
|
|
|
@ -9,6 +9,8 @@
|
|||
|
||||
#if GFX_USE_GDISP && GDISP_NEED_IMAGE && GDISP_NEED_IMAGE_PNG
|
||||
|
||||
#include "gdisp_image_support.h"
|
||||
|
||||
#error "PNG support not implemented yet"
|
||||
|
||||
#endif /* GFX_USE_GDISP && GDISP_NEED_IMAGE && GDISP_NEED_IMAGE_PNG */
|
||||
|
|
109
src/gdisp/gdisp_image_support.h
Normal file
109
src/gdisp/gdisp_image_support.h
Normal file
|
@ -0,0 +1,109 @@
|
|||
/*
|
||||
* This file is subject to the terms of the GFX License. If a copy of
|
||||
* the license was not distributed with this file, you can obtain one at:
|
||||
*
|
||||
* http://ugfx.org/license.html
|
||||
*/
|
||||
|
||||
/**
|
||||
* @file src/gdisp/gdisp_image_support.h
|
||||
* @brief GDISP image support routines header file.
|
||||
*
|
||||
* @defgroup Image Image
|
||||
* @ingroup GDISP
|
||||
* @{
|
||||
*/
|
||||
|
||||
#ifndef _GDISP_IMAGE_SUPPORT_H
|
||||
#define _GDISP_IMAGE_SUPPORT_H
|
||||
|
||||
/* Base endian handling routines */
|
||||
#define gdispImageGetVar(type, p, idx) (*(type *)(((uint8_t *)(p))+(idx)))
|
||||
#define gdispImageGetByte(type, p, idx, shift) (((type)gdispImageGetVar(uint8_t, p, idx))<<(shift))
|
||||
#define gdispImageSwap16(w) ((((uint16_t)(w))>>8)|(((uint16_t)(w))<<8))
|
||||
#define gdispImageSwap32(dw) ((((uint32_t)(w))>>24)|((((uint32_t)(w))&0x00FF0000)>>8)\
|
||||
|((((uint32_t)(w))&0x0000FF00)<<8)|(((uint32_t)(w))<<24))
|
||||
|
||||
/*
|
||||
* Get a uint16_t/uint32_t from memory in the required endianness.
|
||||
* There is no alignment requirement.
|
||||
*/
|
||||
#if GFX_CPU_ENDIAN == GFX_CPU_ENDIAN_LITTLE && GFX_CPU_NO_ALIGNMENT_FAULTS
|
||||
#define gidspImageGetLE16(p, idx) gdispImageGetVar(uint16_t, (p), (idx))
|
||||
#define gidspImageGetLE32(p, idx) gdispImageGetVar(uint32_t, (p), (idx))
|
||||
#else
|
||||
#define gdispImageGetLE16(p, idx) ( gdispImageGetByte(uint16_t, (p), (idx) , 0) | gdispImageGetByte(uint16_t, (p), (idx)+1, 8))
|
||||
#define gdispImageGetLE32(p, idx) ( gdispImageGetByte(uint32_t, (p), (idx) , 0) | gdispImageGetByte(uint32_t, (p), (idx)+1, 8)\
|
||||
|gdispImageGetByte(uint32_t, (p), (idx)+2, 16) | gdispImageGetByte(uint32_t, (p), (idx)+3, 24))
|
||||
#endif
|
||||
#if GFX_CPU_ENDIAN == GFX_CPU_ENDIAN_BIG && GFX_CPU_NO_ALIGNMENT_FAULTS
|
||||
#define gidspImageGetBE16(p, idx) gdispImageGetVar(uint16_t, (p), (idx))
|
||||
#define gidspImageGetBE32(p, idx) gdispImageGetVar(uint32_t, (p), (idx))
|
||||
#else
|
||||
#define gdispImageGetBE16(p, idx) ( gdispImageGetByte(uint16_t, (p), (idx) , 8) | gdispImageGetByte(uint16_t, (p), (idx)+1, 0))
|
||||
#define gdispImageGetBE32(p, idx) ( gdispImageGetByte(uint32_t, (p), (idx) , 24) | gdispImageGetByte(uint32_t, (p), (idx)+1, 16)\
|
||||
|gdispImageGetByte(uint32_t, (p), (idx)+2, 8) | gdispImageGetByte(uint32_t, (p), (idx)+3, 0))
|
||||
#endif
|
||||
|
||||
/*
|
||||
* Get a uint16_t/uint32_t from memory in the required endianness.
|
||||
* These are optimised routines but the memory must be word/dword aligned.
|
||||
*/
|
||||
#if GFX_CPU_ENDIAN == GFX_CPU_ENDIAN_LITTLE
|
||||
#define gdispImageGetAlignedLE16(p, idx) gdispImageGetVar(uint16_t, (p), (idx))
|
||||
#define gdispImageGetAlignedBE16(p, idx) gidspImageGetBE16(p, (idx))
|
||||
#define gdispImageGetAlignedLE32(p, idx) gdispImageGetVar(uint32_t, (p), (idx))
|
||||
#define gdispImageGetAlignedBE32(p, idx) gidspImageGetBE32(p, (idx))
|
||||
#elif GFX_CPU_ENDIAN == GFX_CPU_ENDIAN_BIG
|
||||
#define gdispImageGetAlignedLE16(p, idx) gidspImageGetLE16(p, (idx))
|
||||
#define gdispImageGetAlignedBE16(p, idx) gdispImageGetVar(uint16_t, (p), (idx))
|
||||
#define gdispImageGetAlignedLE32(p, idx) gidspImageGetLE32(p, (idx))
|
||||
#define gdispImageGetAlignedBE32(p, idx) gdispImageGetVar(uint32_t, (p), (idx))
|
||||
#else
|
||||
#define gdispImageGetAlignedLE16(p, idx) gidspImageGetLE16(p, (idx))
|
||||
#define gdispImageGetAlignedBE16(p, idx) gidspImageGetBE16(p, (idx))
|
||||
#define gdispImageGetAlignedLE32(p, idx) gidspImageGetLE32(p, (idx))
|
||||
#define gdispImageGetAlignedBE32(p, idx) gidspImageGetBE32(p, (idx))
|
||||
#endif
|
||||
|
||||
/*
|
||||
* Change a uint16 or uint32 already in a register to the required endianness.
|
||||
*/
|
||||
#if GFX_CPU_ENDIAN == GFX_CPU_ENDIAN_LITTLE
|
||||
#define gdispImageMakeLE16(w)
|
||||
#define gdispImageMakeLE32(dw)
|
||||
#define gdispImageMakeBE16(w) { w = gdispImageSwap16(w); }
|
||||
#define gdispImageMakeBE32(dw) { dw = gdispImageSwap32(dw); }
|
||||
#elif GFX_CPU_ENDIAN == GFX_CPU_ENDIAN_BIG
|
||||
#define gdispImageMakeLE16(w) { w = gdispImageSwap16(w); }
|
||||
#define gdispImageMakeLE32(dw) { dw = gdispImageSwap32(dw); }
|
||||
#define gdispImageMakeBE16(w)
|
||||
#define gdispImageMakeBE32(dw)
|
||||
#else
|
||||
#define gdispImageEndianness() (*(uint32_t *)&gdispImageEndianArray)
|
||||
|
||||
#define gdispImageMakeLE16(w) { if (gdispImageEndianness() != GFX_CPU_ENDIAN_LITTLE) w = gdispImageSwap16(w); }
|
||||
#define gdispImageMakeLE32(dw) { if (gdispImageEndianness() != GFX_CPU_ENDIAN_LITTLE) dw = gdispImageSwap32(dw); }
|
||||
#define gdispImageMakeBE16(w) { if (gdispImageEndianness() != GFX_CPU_ENDIAN_BIG) w = gdispImageSwap16(w); }
|
||||
#define gdispImageMakeBE32(dw) { if (gdispImageEndianness() != GFX_CPU_ENDIAN_BIG) dw = gdispImageSwap32(dw); }
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
void *gdispImageAlloc(gdispImage *img, size_t sz);
|
||||
void gdispImageFree(gdispImage *img, void *ptr, size_t sz);
|
||||
|
||||
#if GFX_CPU_ENDIAN == GFX_CPU_ENDIAN_UNKNOWN
|
||||
extern const uint8_t gdispImageEndianArray[4];
|
||||
#endif
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* _GDISP_IMAGE_SUPPORT_H */
|
||||
/** @} */
|
||||
|
Loading…
Add table
Reference in a new issue