A basic graphics package for the LPC4088 Display Module.

Dependents:   lpc4088_displaymodule_demo_sphere sampleGUI sampleEmptyGUI lpc4088_displaymodule_fs_aid ... more

Fork of DMBasicGUI by EmbeddedArtists AB

Revision:
0:4977187e90c7
Child:
1:46c8df4608c8
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/Application/Image.cpp	Thu Dec 11 11:03:57 2014 +0000
@@ -0,0 +1,188 @@
+
+#include "mbed.h"
+#include "Image.h"
+
+#include "bmp.h"
+#include "lodepng.h"
+
+int Image::decode(const unsigned char* pDataIn, unsigned int sizeIn, Resolution resolution, ImageData_t* pDataOut)
+{
+  Image::Type type = imageType(pDataIn, sizeIn);
+  int result = -1;
+  switch (type)
+  {
+    case BMP:
+    {
+      struct BMPHeader* hdr = (struct BMPHeader *) pDataIn;
+      if (resolution == RES_16BIT) {
+        pDataOut->pixels = (uint16_t*)malloc(hdr->width * hdr->height * 2);
+      } else if (resolution == RES_24BIT) {
+        pDataOut->pixels = (uint16_t*)malloc(hdr->width * hdr->height * 4);
+      } else {
+        return -1;
+      }
+      if (pDataOut->pixels != NULL)
+      {
+        unsigned char error = BMP_Decode((void*)pDataIn, (unsigned char*)pDataOut->pixels, 
+                                         hdr->width, hdr->height, 24, ((resolution == RES_16BIT) ? 16 : 24));
+        if (error == 0)
+        {
+          pDataOut->width = hdr->width;
+          pDataOut->height = hdr->height;
+          pDataOut->res = resolution;
+          return 0;
+        }
+        free(pDataOut->pixels);
+      }
+    }
+    break;
+      
+    case PNG:
+    {
+      unsigned char* pTmp;
+      unsigned error = lodepng_decode24(&pTmp, &pDataOut->width, &pDataOut->height, pDataIn, sizeIn);
+      pDataOut->res = resolution;
+      if (error == 0)
+      {
+        int x, y;
+        uint8_t r;
+        uint8_t g;
+        uint8_t b;
+        int off = 0;
+    
+        result = 0;
+        if (resolution == RES_16BIT) {
+            pDataOut->pixels = (uint16_t*)malloc(pDataOut->width * pDataOut->height * 2);
+            if (pDataOut->pixels != NULL)
+            {
+                uint16_t* pConverted = pDataOut->pixels;
+            
+                for (y = 0; y < pDataOut->height; y++) {
+                  for (x = 0; x < pDataOut->width; x++) {
+                    r = pTmp[off    ];
+                    g = pTmp[off + 1];
+                    b = pTmp[off + 2];
+                    *pConverted = (((unsigned short)r & 0xF8) << 8) |
+                                   (((unsigned short)g & 0xFC) << 3) |
+                                   (((unsigned short)b & 0xF8) >> 3);
+                    pConverted++;
+                    off += 3;
+                  }
+                }
+            }
+        } else if (resolution == RES_24BIT) {
+            uint32_t* pConverted = (uint32_t*)malloc(pDataOut->width * pDataOut->height * 4);
+            pDataOut->pixels = (uint16_t*)pConverted;
+            if (pDataOut->pixels != NULL)
+            {
+                uint8_t* p = pTmp;
+                int num = pDataOut->width * pDataOut->height;
+                for (int i = 0; i < num; i++) {
+                    uint32_t a = 0;
+                    a |= (*p++) << 16;  // red
+                    a |= (*p++) <<  8;  // green
+                    a |= (*p++) <<  0;  // blue
+                    *pConverted++ = a;
+//                    *pConverted++ = 0;    // alpha
+//                    *pConverted++ = *p++; // red
+//                    *pConverted++ = *p++; // green
+//                    *pConverted++ = *p++; // blue
+                }
+            }
+        } else {
+            // unknown format
+            result = -2;
+        }
+        free(pTmp);
+        return result;
+      }
+    }
+    break;
+    
+    default:
+      break;
+  }
+  
+  pDataOut->pixels = NULL;
+  pDataOut->width = 0;
+  pDataOut->height = 0;
+  return result;
+}
+
+int Image::decode(const char* filename, Resolution res, ImageData_t* pDataOut)
+{
+  FILE* fh = NULL;
+  uint8_t* buff = NULL;
+  int result = 1;
+
+  do 
+  {
+    fh = fopen(filename, "r");
+    if (fh == NULL) {
+      break;
+    }
+    
+    uint32_t size = fileSize(fh);
+    buff = (uint8_t*)malloc(size);
+    if (buff == NULL) {
+      return 1;
+    }
+    
+    uint32_t num;
+    uint32_t left = size;
+    uint32_t off = 0;
+    do
+    {
+      num = fread(buff+off, 1, left, fh);
+      if (num > 0) {
+        left -= num;
+        off += num;
+      }
+    } while (left > 0 && num > 0);
+    if (left > 0) {
+      break;
+    }
+    
+    if (Image::decode(buff, size, res, pDataOut) == 1) {
+      break;
+    }
+    
+    // success
+    result = 0;
+    
+  } while (false);
+  
+  if (fh != NULL) {
+    fclose(fh);
+  }
+  if (buff != NULL) {
+    free(buff);
+  }
+  return result;
+}
+
+Image::Type Image::imageType(const unsigned char* pDataIn, unsigned int sizeIn)
+{
+  if (sizeIn > 4)
+  {
+    if (pDataIn[0] == 0x89 && pDataIn[1] == 'P' && pDataIn[2] == 'N' && pDataIn[3] == 'G')
+    {
+      return PNG;
+    }
+  }
+  if (BMP_IsValid((void*)pDataIn))
+  {
+    return BMP;
+  }
+  return UNKNOWN;
+}
+
+uint32_t Image::fileSize(FILE* f)
+{
+  uint32_t pos = ftell(f);
+  fseek(f, 0, SEEK_END);
+  uint32_t size = ftell(f);
+  fseek(f, pos, SEEK_SET);
+  return size;
+}
+