Arducam_UTFT_SPI_Library

Dependents:   DigitalCamera_OV5642_WIZwiki-W7500 Prelude_OV5642_dev

Files at this revision

API Documentation at this revision

Comitter:
justinkim
Date:
Thu Oct 29 06:26:48 2015 +0000
Commit message:
spi test failed

Changed in this revision

UTFT_SPI.cpp Show annotated file Show diff for this revision Revisions of this file
UTFT_SPI.h Show annotated file Show diff for this revision Revisions of this file
diff -r 000000000000 -r 53f8d6b23687 UTFT_SPI.cpp
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/UTFT_SPI.cpp	Thu Oct 29 06:26:48 2015 +0000
@@ -0,0 +1,1013 @@
+/*
+  UTFT.cpp - Arduino library support for Color TFT LCD Boards
+  This is special porting for ArduCAM shield LCD screen. 
+  Use SPI bus interface and SSD1289 controller. Only work on 
+  ArduCAM shield Rev.C.
+  For more information about ArduCAM shield please visit
+  www.arducam.com
+  Copyright (C)2010-2014 Henning Karlsen. All right reserved
+  
+  This library is the continuation of my ITDB02_Graph, ITDB02_Graph16
+  and RGB_GLCD libraries for Arduino and chipKit. As the number of 
+  supported display modules and controllers started to increase I felt 
+  it was time to make a single, universal library as it will be much 
+  easier to maintain in the future.
+
+  Basic functionality of this library was origianlly based on the 
+  demo-code provided by ITead studio (for the ITDB02 modules) and 
+  NKC Electronics (for the RGB GLCD module/shield).
+
+  This library supports a number of 8bit, 16bit and serial graphic 
+  displays, and will work with both Arduino and chipKit boards. For a 
+  full list of tested display modules and controllers, see the 
+  document UTFT_Supported_display_modules_&_controllers.pdf.
+
+  When using 8bit and 16bit display modules there are some 
+  requirements you must adhere to. These requirements can be found 
+  in the document UTFT_Requirements.pdf.
+  There are no special requirements when using serial displays.
+
+  You can always find the latest version of the library at 
+  http://electronics.henningkarlsen.com/
+
+  If you make any modifications or improvements to the code, I would 
+  appreciate that you share the code with me so that I might include 
+  it in the next release. I can be contacted through 
+  http://electronics.henningkarlsen.com/contact.php.
+
+  This library is free software; you can redistribute it and/or
+  modify it under the terms of the GNU Lesser General Public
+  License as published by the Free Software Foundation; either
+  version 2.1 of the License, or (at your option) any later version.
+
+  This library is distributed in the hope that it will be useful,
+  but WITHOUT ANY WARRANTY; without even the implied warranty of
+  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+  Lesser General Public License for more details.
+
+  You should have received a copy of the GNU Lesser General Public
+  License along with this library; if not, write to the Free Software
+  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+*/
+
+#include "mbed.h"
+#include "UTFT_SPI.h"
+
+ArduLCD::ArduLCD(PinName mosi, PinName miso, PinName sck, PinName cs)
+        : spi(mosi,miso,sck), _cs(cs)
+{   
+    //Must initialize the Bus default status
+    _cs = 1;
+    model = SSD1289;
+    disp_x_size=239;
+    disp_y_size=319;
+    display_transfer_mode=8;
+
+    display_model=model;
+
+    //_set_direction_registers(display_transfer_mode);
+    //P_CS  = portOutputRegister(digitalPinToPort(CS));
+    //B_CS  = digitalPinToBitMask(CS);
+    //pinMode(CS,OUTPUT);
+}
+
+int ArduLCD::bus_write(int address, int value) 
+{
+  _cs = 0;
+  spi.write(address);
+  spi.write(value);
+  _cs = 1;
+  return value;
+}
+
+uint8_t ArduLCD::bus_read(int address) 
+{
+  uint8_t value = 0;
+  _cs = 0;
+  spi.write(address);
+  value = spi.write(0x00);
+  _cs = 1;
+  return value;
+}
+
+void ArduLCD::LCD_Write_COM(char VL)  
+{   
+    bus_write(0xBE, VL);
+}
+
+void ArduLCD::LCD_Write_DATA(char VH,char VL)
+{
+    bus_write(0xBF, VH);
+    bus_write(0xBF, VL);
+}
+
+void ArduLCD::LCD_Write_COM_DATA(char com1,int dat1)
+{
+     LCD_Write_COM(com1);
+     LCD_Write_DATA(dat1>>8,dat1);
+     
+}
+
+void ArduLCD::LCD_Writ_Bus(char VH,char VL)
+{
+    LCD_Write_DATA(VH,VL);
+}
+
+void ArduLCD::InitLCD(uint8_t orientation)
+{
+    orient=orientation;
+
+    LCD_Write_COM_DATA(0x00,0x0001);
+    LCD_Write_COM_DATA(0x03,0xA8A4);
+    LCD_Write_COM_DATA(0x0C,0x0000);
+    LCD_Write_COM_DATA(0x0D,0x080C);
+    LCD_Write_COM_DATA(0x0E,0x2B00);
+    LCD_Write_COM_DATA(0x1E,0x00B7);
+    LCD_Write_COM_DATA(0x01,0x693F);
+    LCD_Write_COM_DATA(0x02,0x0600);
+    LCD_Write_COM_DATA(0x10,0x0000);
+    LCD_Write_COM_DATA(0x11,0x6078);
+    LCD_Write_COM_DATA(0x05,0x0000);
+    LCD_Write_COM_DATA(0x06,0x0000);
+    LCD_Write_COM_DATA(0x16,0xEF1C);
+    LCD_Write_COM_DATA(0x17,0x0003);
+    LCD_Write_COM_DATA(0x07,0x0233);
+    LCD_Write_COM_DATA(0x0B,0x0000);
+    LCD_Write_COM_DATA(0x0F,0x0000);
+    LCD_Write_COM_DATA(0x41,0x0000);
+    LCD_Write_COM_DATA(0x42,0x0000);
+    LCD_Write_COM_DATA(0x48,0x0000);
+    LCD_Write_COM_DATA(0x49,0x013F);
+    LCD_Write_COM_DATA(0x4A,0x0000);
+    LCD_Write_COM_DATA(0x4B,0x0000);
+    LCD_Write_COM_DATA(0x44,0xEF00);
+    LCD_Write_COM_DATA(0x45,0x0000);
+    LCD_Write_COM_DATA(0x46,0x013F);
+    LCD_Write_COM_DATA(0x30,0x0707);
+    LCD_Write_COM_DATA(0x31,0x0204);
+    LCD_Write_COM_DATA(0x32,0x0204);
+    LCD_Write_COM_DATA(0x33,0x0502);
+    LCD_Write_COM_DATA(0x34,0x0507);
+    LCD_Write_COM_DATA(0x35,0x0204);
+    LCD_Write_COM_DATA(0x36,0x0204);
+    LCD_Write_COM_DATA(0x37,0x0502);
+    LCD_Write_COM_DATA(0x3A,0x0302);
+    LCD_Write_COM_DATA(0x3B,0x0302);
+    LCD_Write_COM_DATA(0x23,0x0000);
+    LCD_Write_COM_DATA(0x24,0x0000);
+    LCD_Write_COM_DATA(0x25,0x8000);
+    LCD_Write_COM_DATA(0x4f,0x0000);
+    LCD_Write_COM_DATA(0x4e,0x0000);
+    LCD_Write_COM(0x22);
+
+    //setColor(255, 255, 255);
+    //setBackColor(0, 0, 0);
+    cfont.font=0;
+    clrScr();
+}
+
+void ArduLCD::setXY(uint16_t x1, uint16_t y1, uint16_t x2, uint16_t y2)
+{
+    if (orient==LANDSCAPE)
+    {
+        swap(uint16_t, x1, y1);
+        swap(uint16_t, x2, y2)
+        y1=disp_y_size-y1;
+        y2=disp_y_size-y2;
+        swap(uint16_t, y1, y2)
+    }
+    
+    LCD_Write_COM_DATA(0x44,(x2<<8)+x1);
+    LCD_Write_COM_DATA(0x45,y1);
+    LCD_Write_COM_DATA(0x46,y2);
+    LCD_Write_COM_DATA(0x4e,x1);
+    LCD_Write_COM_DATA(0x4f,y1);
+    LCD_Write_COM(0x22);
+}
+
+void ArduLCD::clrXY()
+{
+    if (orient==PORTRAIT)
+        setXY(0,0,disp_x_size,disp_y_size);
+    else
+        setXY(0,0,disp_y_size,disp_x_size);
+}
+
+void ArduLCD::resetXY()
+{
+    clrXY();
+}
+
+void ArduLCD::drawRect(int x1, int y1, int x2, int y2)
+{
+    if (x1>x2)
+    {
+        swap(int, x1, x2);
+    }
+    if (y1>y2)
+    {
+        swap(int, y1, y2);
+    }
+
+    drawHLine(x1, y1, x2-x1);
+    drawHLine(x1, y2, x2-x1);
+    drawVLine(x1, y1, y2-y1);
+    drawVLine(x2, y1, y2-y1);
+}
+
+void ArduLCD::drawRoundRect(int x1, int y1, int x2, int y2)
+{
+    if (x1>x2)
+    {
+        swap(int, x1, x2);
+    }
+    if (y1>y2)
+    {
+        swap(int, y1, y2);
+    }
+    if ((x2-x1)>4 && (y2-y1)>4)
+    {
+        drawPixel(x1+1,y1+1);
+        drawPixel(x2-1,y1+1);
+        drawPixel(x1+1,y2-1);
+        drawPixel(x2-1,y2-1);
+        drawHLine(x1+2, y1, x2-x1-4);
+        drawHLine(x1+2, y2, x2-x1-4);
+        drawVLine(x1, y1+2, y2-y1-4);
+        drawVLine(x2, y1+2, y2-y1-4);
+    }
+}
+
+void ArduLCD::fillRect(int x1, int y1, int x2, int y2)
+{
+    if (x1>x2)
+    {
+        swap(int, x1, x2);
+    }
+    if (y1>y2)
+    {
+        swap(int, y1, y2);
+    }
+    
+    if (orient==PORTRAIT)
+    {
+        for (int i=0; i<((y2-y1)/2)+1; i++)
+        {
+            drawHLine(x1, y1+i, x2-x1);
+            drawHLine(x1, y2-i, x2-x1);
+        }
+    }
+    else
+    {
+        for (int i=0; i<((x2-x1)/2)+1; i++)
+        {
+            drawVLine(x1+i, y1, y2-y1);
+            drawVLine(x2-i, y1, y2-y1);
+        }
+    }
+}
+
+void ArduLCD::fillRoundRect(int x1, int y1, int x2, int y2)
+{
+    if (x1>x2)
+    {
+        swap(int, x1, x2);
+    }
+    if (y1>y2)
+    {
+        swap(int, y1, y2);
+    }
+
+    if ((x2-x1)>4 && (y2-y1)>4)
+    {
+        for (int i=0; i<((y2-y1)/2)+1; i++)
+        {
+            switch(i)
+            {
+            case 0:
+                drawHLine(x1+2, y1+i, x2-x1-4);
+                drawHLine(x1+2, y2-i, x2-x1-4);
+                break;
+            case 1:
+                drawHLine(x1+1, y1+i, x2-x1-2);
+                drawHLine(x1+1, y2-i, x2-x1-2);
+                break;
+            default:
+                drawHLine(x1, y1+i, x2-x1);
+                drawHLine(x1, y2-i, x2-x1);
+            }
+        }
+    }
+}
+
+void ArduLCD::drawCircle(int x, int y, int radius)
+{
+    int f = 1 - radius;
+    int ddF_x = 1;
+    int ddF_y = -2 * radius;
+    int x1 = 0;
+    int y1 = radius;
+ 
+    _cs = 0;
+    setXY(x, y + radius, x, y + radius);
+    LCD_Write_DATA(fch,fcl);
+    setXY(x, y - radius, x, y - radius);
+    LCD_Write_DATA(fch,fcl);
+    setXY(x + radius, y, x + radius, y);
+    LCD_Write_DATA(fch,fcl);
+    setXY(x - radius, y, x - radius, y);
+    LCD_Write_DATA(fch,fcl);
+ 
+    while(x1 < y1)
+    {
+        if(f >= 0) 
+        {
+            y1--;
+            ddF_y += 2;
+            f += ddF_y;
+        }
+        x1++;
+        ddF_x += 2;
+        f += ddF_x;    
+        setXY(x + x1, y + y1, x + x1, y + y1);
+        LCD_Write_DATA(fch,fcl);
+        setXY(x - x1, y + y1, x - x1, y + y1);
+        LCD_Write_DATA(fch,fcl);
+        setXY(x + x1, y - y1, x + x1, y - y1);
+        LCD_Write_DATA(fch,fcl);
+        setXY(x - x1, y - y1, x - x1, y - y1);
+        LCD_Write_DATA(fch,fcl);
+        setXY(x + y1, y + x1, x + y1, y + x1);
+        LCD_Write_DATA(fch,fcl);
+        setXY(x - y1, y + x1, x - y1, y + x1);
+        LCD_Write_DATA(fch,fcl);
+        setXY(x + y1, y - x1, x + y1, y - x1);
+        LCD_Write_DATA(fch,fcl);
+        setXY(x - y1, y - x1, x - y1, y - x1);
+        LCD_Write_DATA(fch,fcl);
+    }
+    _cs = 1;
+    clrXY();
+}
+
+void ArduLCD::fillCircle(int x, int y, int radius)
+{
+    for(int y1=-radius; y1<=0; y1++) 
+        for(int x1=-radius; x1<=0; x1++)
+            if(x1*x1+y1*y1 <= radius*radius) 
+            {
+                drawHLine(x+x1, y+y1, 2*(-x1));
+                drawHLine(x+x1, y-y1, 2*(-x1));
+                break;
+            }
+}
+
+void ArduLCD::clrScr()
+{
+    long i;
+    
+    clrXY();
+
+    for (i=0; i<((disp_x_size+1)*(disp_y_size+1)); i++)
+    {
+        if (display_transfer_mode!=1)
+            LCD_Writ_Bus(0x00,0x00);
+        else
+        {
+            LCD_Writ_Bus(1,0);
+            LCD_Writ_Bus(1,0);
+            
+            //LCD_Writ_Bus(00,0x55);
+        }
+        //delay(1);
+#if defined(ESP8266)    
+      yield();  
+#endif    
+    }
+}
+
+void ArduLCD::fillScr(uint8_t r, uint8_t g, uint8_t b)
+{
+    uint16_t color = ((r&248)<<8 | (g&252)<<3 | (b&248)>>3);
+    fillScr(color);
+}
+
+void ArduLCD::fillScr(uint16_t color)
+{
+    long i;
+    char ch, cl;
+    
+    ch=uint8_t(color>>8);
+    cl=uint8_t(color & 0xFF);
+
+    clrXY();
+    
+    for (i=0; i<((disp_x_size+1)*(disp_y_size+1)); i++)
+    {
+        if (display_transfer_mode!=1)
+            LCD_Writ_Bus(ch,cl);
+        else
+        {
+            LCD_Writ_Bus(1,ch);
+            LCD_Writ_Bus(1,cl);
+        }
+#if defined(ESP8266)    
+      yield();  
+#endif          
+    }
+
+}
+
+void ArduLCD::setColor(uint8_t r, uint8_t g, uint8_t b)
+{
+    fch=((r&248)|g>>5);
+    fcl=((g&28)<<3|b>>3);
+}
+
+void ArduLCD::setColor(uint16_t color)
+{
+    fch=uint8_t(color>>8);
+    fcl=uint8_t(color & 0xFF);
+}
+
+uint16_t ArduLCD::getColor()
+{
+    return (fch<<8) | fcl;
+}
+
+void ArduLCD::setBackColor(uint8_t r, uint8_t g, uint8_t b)
+{
+    bch=((r&248)|g>>5);
+    bcl=((g&28)<<3|b>>3);
+    _transparent=false;
+}
+
+void ArduLCD::setBackColor(uint32_t color)
+{
+    if (color==VGA_TRANSPARENT)
+        _transparent=true;
+    else
+    {
+        bch=uint8_t(color>>8);
+        bcl=uint8_t(color & 0xFF);
+        _transparent=false;
+    }
+}
+
+uint16_t ArduLCD::getBackColor()
+{
+    return (bch<<8) | bcl;
+}
+
+void ArduLCD::setPixel(uint16_t color)
+{
+    LCD_Write_DATA((color>>8),(color&0xFF));    // rrrrrggggggbbbbb
+}
+
+void ArduLCD::drawPixel(int x, int y)
+{
+    setXY(x, y, x, y);
+    setPixel((fch<<8)|fcl);
+    clrXY();
+}
+
+void ArduLCD::drawLine(int x1, int y1, int x2, int y2)
+{
+    if (y1==y2)
+        drawHLine(x1, y1, x2-x1);
+    else if (x1==x2)
+        drawVLine(x1, y1, y2-y1);
+    else
+    {
+        unsigned int    dx = (x2 > x1 ? x2 - x1 : x1 - x2);
+        short           xstep =  x2 > x1 ? 1 : -1;
+        unsigned int    dy = (y2 > y1 ? y2 - y1 : y1 - y2);
+        short           ystep =  y2 > y1 ? 1 : -1;
+        int             col = x1, row = y1;
+
+        if (dx < dy)
+        {
+            int t = - (dy >> 1);
+            while (true)
+            {
+                setXY (col, row, col, row);
+                LCD_Write_DATA (fch, fcl);
+                if (row == y2)
+                    return;
+                row += ystep;
+                t += dx;
+                if (t >= 0)
+                {
+                    col += xstep;
+                    t   -= dy;
+                }
+            } 
+        }
+        else
+        {
+            int t = - (dx >> 1);
+            while (true)
+            {
+                setXY (col, row, col, row);
+                LCD_Write_DATA (fch, fcl);
+                if (col == x2)
+                    return;
+                col += xstep;
+                t += dy;
+                if (t >= 0)
+                {
+                    row += ystep;
+                    t   -= dx;
+                }
+            } 
+        }
+    }
+    clrXY();
+}
+
+void ArduLCD::drawHLine(int x, int y, int l)
+{
+    if (l<0)
+    {
+        l = -l;
+        x -= l;
+    }
+    setXY(x, y, x+l, y);
+    if (display_transfer_mode == 16)
+    {
+        _fast_fill_16(fch,fcl,l);
+    }
+    else if ((display_transfer_mode==8) and (fch==fcl))
+    {
+        _fast_fill_8(fch,l);
+    }
+    else
+    {
+        for (int i=0; i<l+1; i++)
+        {
+            LCD_Write_DATA(fch, fcl);
+        }
+    }
+    clrXY();
+}
+
+void ArduLCD::drawVLine(int x, int y, int l)
+{
+    if (l<0)
+    {
+        l = -l;
+        y -= l;
+    }
+    setXY(x, y, x, y+l);
+    if (display_transfer_mode == 16)
+    {
+        _fast_fill_16(fch,fcl,l);
+    }
+    else if ((display_transfer_mode==8) and (fch==fcl))
+    {
+        _fast_fill_8(fch,l);
+    }
+    else
+    {
+        for (int i=0; i<l+1; i++)
+        {
+            LCD_Write_DATA(fch, fcl);
+        }
+    }
+    clrXY();
+}
+/*
+void ArduLCD::printChar(uint8_t c, int x, int y)
+{
+    uint8_t i,ch;
+    uint16_t j;
+    uint16_t temp; 
+  
+    if (!_transparent)
+    {
+        if (orient==PORTRAIT)
+        {
+            setXY(x,y,x+cfont.x_size-1,y+cfont.y_size-1);
+      
+            temp=((c-cfont.offset)*((cfont.x_size/8)*cfont.y_size))+4;
+            for(j=0;j<((cfont.x_size/8)*cfont.y_size);j++)
+            {
+                ch=pgm_read_byte(&cfont.font[temp]);
+                for(i=0;i<8;i++)
+                {   
+                    if((ch&(1<<(7-i)))!=0)   
+                    {
+                        setPixel((fch<<8)|fcl);
+                    } 
+                    else
+                    {
+                        setPixel((bch<<8)|bcl);
+                    }   
+                }
+                temp++;
+            }
+        }
+        else
+        {
+            temp=((c-cfont.offset)*((cfont.x_size/8)*cfont.y_size))+4;
+
+            for(j=0;j<((cfont.x_size/8)*cfont.y_size);j+=(cfont.x_size/8))
+            {
+                setXY(x,y+(j/(cfont.x_size/8)),x+cfont.x_size-1,y+(j/(cfont.x_size/8)));
+                for (int zz=(cfont.x_size/8)-1; zz>=0; zz--)
+                {
+                    ch=pgm_read_byte(&cfont.font[temp+zz]);
+                    for(i=0;i<8;i++)
+                    {   
+                        if((ch&(1<<i))!=0)   
+                        {
+                            setPixel((fch<<8)|fcl);
+                        } 
+                        else
+                        {
+                            setPixel((bch<<8)|bcl);
+                        }   
+                    }
+                }
+                temp+=(cfont.x_size/8);
+            }
+        }
+    }
+    else
+    {
+        temp=((c-cfont.offset)*((cfont.x_size/8)*cfont.y_size))+4;
+        for(j=0;j<cfont.y_size;j++) 
+        {
+            for (int zz=0; zz<(cfont.x_size/8); zz++)
+            {
+                ch=pgm_read_byte(&cfont.font[temp+zz]); 
+                for(i=0;i<8;i++)
+                {   
+                    setXY(x+i+(zz*8),y+j,x+i+(zz*8)+1,y+j+1);
+                
+                    if((ch&(1<<(7-i)))!=0)   
+                    {
+                        setPixel((fch<<8)|fcl);
+                    } 
+                }
+            }
+            temp+=(cfont.x_size/8);
+        }
+    }
+    clrXY();
+}
+
+void ArduLCD::rotateChar(uint8_t c, int x, int y, int pos, int deg)
+{
+    uint8_t i,j,ch;
+    uint16_t temp; 
+    int newx,newy;
+    double radian;
+    radian=deg*0.0175;  
+
+    temp=((c-cfont.offset)*((cfont.x_size/8)*cfont.y_size))+4;
+    for(j=0;j<cfont.y_size;j++) 
+    {
+        for (int zz=0; zz<(cfont.x_size/8); zz++)
+        {
+            ch=pgm_read_byte(&cfont.font[temp+zz]); 
+            for(i=0;i<8;i++)
+            {   
+                newx=x+(((i+(zz*8)+(pos*cfont.x_size))*cos(radian))-((j)*sin(radian)));
+                newy=y+(((j)*cos(radian))+((i+(zz*8)+(pos*cfont.x_size))*sin(radian)));
+
+                setXY(newx,newy,newx+1,newy+1);
+                
+                if((ch&(1<<(7-i)))!=0)   
+                {
+                    setPixel((fch<<8)|fcl);
+                } 
+                else  
+                {
+                    if (!_transparent)
+                        setPixel((bch<<8)|bcl);
+                }   
+            }
+        }
+        temp+=(cfont.x_size/8);
+    }
+    clrXY();
+}
+
+void ArduLCD::print(char *st, int x, int y, int deg)
+{
+    int stl, i;
+
+    stl = strlen(st);
+
+    if (orient==PORTRAIT)
+    {
+    if (x==RIGHT)
+        x=(disp_x_size+1)-(stl*cfont.x_size);
+    if (x==CENTER)
+        x=((disp_x_size+1)-(stl*cfont.x_size))/2;
+    }
+    else
+    {
+    if (x==RIGHT)
+        x=(disp_y_size+1)-(stl*cfont.x_size);
+    if (x==CENTER)
+        x=((disp_y_size+1)-(stl*cfont.x_size))/2;
+    }
+
+    for (i=0; i<stl; i++)
+        if (deg==0)
+            printChar(*st++, x + (i*(cfont.x_size)), y);
+        else
+            rotateChar(*st++, x, y, i, deg);
+}
+
+void ArduLCD::print(string st, int x, int y, int deg)
+{
+    char buf[st.length()+1];
+
+    st.toCharArray(buf, st.length()+1);
+    print(buf, x, y, deg);
+}
+
+void ArduLCD::printNumI(long num, int x, int y, int length, char filler)
+{
+    char buf[25];
+    char st[27];
+    bool neg=false;
+    int c=0, f=0;
+  
+    if (num==0)
+    {
+        if (length!=0)
+        {
+            for (c=0; c<(length-1); c++)
+                st[c]=filler;
+            st[c]=48;
+            st[c+1]=0;
+        }
+        else
+        {
+            st[0]=48;
+            st[1]=0;
+        }
+    }
+    else
+    {
+        if (num<0)
+        {
+            neg=true;
+            num=-num;
+        }
+      
+        while (num>0)
+        {
+            buf[c]=48+(num % 10);
+            c++;
+            num=(num-(num % 10))/10;
+        }
+        buf[c]=0;
+      
+        if (neg)
+        {
+            st[0]=45;
+        }
+      
+        if (length>(c+neg))
+        {
+            for (int i=0; i<(length-c-neg); i++)
+            {
+                st[i+neg]=filler;
+                f++;
+            }
+        }
+
+        for (int i=0; i<c; i++)
+        {
+            st[i+neg+f]=buf[c-i-1];
+        }
+        st[c+neg+f]=0;
+
+    }
+
+    print(st,x,y);
+}
+
+void ArduLCD::printNumF(double num, uint8_t dec, int x, int y, char divider, int length, char filler)
+{
+    char st[27];
+    bool neg=false;
+
+    if (dec<1)
+        dec=1;
+    else if (dec>5)
+        dec=5;
+
+    if (num<0)
+        neg = true;
+
+    _convert_float(st, num, length, dec);
+
+    if (divider != '.')
+    {
+        for (int i=0; i<sizeof(st); i++)
+            if (st[i]=='.')
+                st[i]=divider;
+    }
+
+    if (filler != ' ')
+    {
+        if (neg)
+        {
+            st[0]='-';
+            for (int i=1; i<sizeof(st); i++)
+                if ((st[i]==' ') || (st[i]=='-'))
+                    st[i]=filler;
+        }
+        else
+        {
+            for (int i=0; i<sizeof(st); i++)
+                if (st[i]==' ')
+                    st[i]=filler;
+        }
+    }
+
+    print(st,x,y);
+}
+
+void ArduLCD::setFont(uint8_t* font)
+{
+    cfont.font=font;
+    cfont.x_size=fontbyte(0);
+    cfont.y_size=fontbyte(1);
+    cfont.offset=fontbyte(2);
+    cfont.numchars=fontbyte(3);
+}
+
+uint8_t* ArduLCD::getFont()
+{
+    return cfont.font;
+}
+
+uint8_t ArduLCD::getFontXsize()
+{
+    return cfont.x_size;
+}
+
+uint8_t ArduLCD::getFontYsize()
+{
+    return cfont.y_size;
+}*/
+
+void ArduLCD::drawBitmap(int x, int y, int sx, int sy, bitmapdatatype data, int scale)
+{
+    unsigned int col;
+    int tx, ty, tc, tsx, tsy;
+
+    if (scale==1)
+    {
+        if (orient==PORTRAIT)
+        {
+            setXY(x, y, x+sx-1, y+sy-1);
+            for (tc=0; tc<(sx*sy); tc++)
+            {
+                col=pgm_read_word(&data[tc]);
+                LCD_Write_DATA(col>>8,col & 0xff);
+            }
+        }
+        else
+        {
+            for (ty=0; ty<sy; ty++)
+            {
+                setXY(x, y+ty, x+sx-1, y+ty);
+                for (tx=sx-1; tx>=0; tx--)
+                {
+                    col=pgm_read_word(&data[(ty*sx)+tx]);
+                    LCD_Write_DATA(col>>8,col & 0xff);
+                }
+            }
+        }
+    }
+    else
+    {
+        if (orient==PORTRAIT)
+        {
+            for (ty=0; ty<sy; ty++)
+            {
+                setXY(x, y+(ty*scale), x+((sx*scale)-1), y+(ty*scale)+scale);
+                for (tsy=0; tsy<scale; tsy++)
+                    for (tx=0; tx<sx; tx++)
+                    {
+                        col=pgm_read_word(&data[(ty*sx)+tx]);
+                        for (tsx=0; tsx<scale; tsx++)
+                            LCD_Write_DATA(col>>8,col & 0xff);
+                    }
+            }
+        }
+        else
+        {
+            for (ty=0; ty<sy; ty++)
+            {
+                for (tsy=0; tsy<scale; tsy++)
+                {
+                    setXY(x, y+(ty*scale)+tsy, x+((sx*scale)-1), y+(ty*scale)+tsy);
+                    for (tx=sx-1; tx>=0; tx--)
+                    {
+                        col=pgm_read_word(&data[(ty*sx)+tx]);
+                        for (tsx=0; tsx<scale; tsx++)
+                            LCD_Write_DATA(col>>8,col & 0xff);
+                    }
+                }
+            }
+        }
+    }
+    clrXY();
+}
+
+void ArduLCD::drawBitmap(int x, int y, int sx, int sy, bitmapdatatype data, int deg, int rox, int roy)
+{
+    unsigned int col;
+    int tx, ty, newx, newy;
+    double radian;
+    radian=deg*0.0175;  
+
+    if (deg==0)
+        drawBitmap(x, y, sx, sy, data);
+    else
+    {
+        for (ty=0; ty<sy; ty++)
+            for (tx=0; tx<sx; tx++)
+            {
+                col=pgm_read_word(&data[(ty*sx)+tx]);
+
+                newx=x+rox+(((tx-rox)*cos(radian))-((ty-roy)*sin(radian)));
+                newy=y+roy+(((ty-roy)*cos(radian))+((tx-rox)*sin(radian)));
+
+                setXY(newx, newy, newx, newy);
+                LCD_Write_DATA(col>>8,col & 0xff);
+            }
+    }
+    clrXY();
+}
+
+void ArduLCD::lcdOff()
+{
+
+}
+
+void ArduLCD::lcdOn()
+{
+
+}
+
+void ArduLCD::setContrast(char c)
+{
+
+}
+
+int ArduLCD::getDisplayXSize()
+{
+    if (orient==PORTRAIT)
+        return disp_x_size+1;
+    else
+        return disp_y_size+1;
+}
+
+int ArduLCD::getDisplayYSize()
+{
+    if (orient==PORTRAIT)
+        return disp_y_size+1;
+    else
+        return disp_x_size+1;
+}
+
+void ArduLCD::_fast_fill_16(int ch, int cl, long pix)
+{
+
+}
+
+void ArduLCD::_fast_fill_8(int ch, long pix)
+{
+
+}
+
+void ArduLCD::setBrightness(uint8_t br)
+{
+
+}
+
+void ArduLCD::setDisplayPage(uint8_t page)
+{
+
+}
+
+void ArduLCD::setWritePage(uint8_t page)
+{
+
+}
+
+void ArduLCD::_convert_float(char *buf, double num, int width, uint8_t prec)
+{
+    
+}
+
diff -r 000000000000 -r 53f8d6b23687 UTFT_SPI.h
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/UTFT_SPI.h	Thu Oct 29 06:26:48 2015 +0000
@@ -0,0 +1,293 @@
+/*
+  UTFT_SPI.h - Arduino library support for Color TFT LCD Boards
+  This is special porting for ArduCAM shield LCD screen. 
+  Use SPI bus interface and SSD1289 controller. Only work on 
+  ArduCAM shield Rev.C.
+  For more information about ArduCAM shield please visit
+  www.arducam.com
+  Copyright (C)2010-2014 Henning Karlsen. All right reserved
+  
+  This library is the continuation of my ITDB02_Graph, ITDB02_Graph16
+  and RGB_GLCD libraries for Arduino and chipKit. As the number of 
+  supported display modules and controllers started to increase I felt 
+  it was time to make a single, universal library as it will be much 
+  easier to maintain in the future.
+
+  Basic functionality of this library was origianlly based on the 
+  demo-code provided by ITead studio (for the ITDB02 modules) and 
+  NKC Electronics (for the RGB GLCD module/shield).
+
+  This library supports a number of 8bit, 16bit and serial graphic 
+  displays, and will work with both Arduino and chipKit boards. For a 
+  full list of tested display modules and controllers, see the 
+  document UTFT_Supported_display_modules_&_controllers.pdf.
+
+  When using 8bit and 16bit display modules there are some 
+  requirements you must adhere to. These requirements can be found 
+  in the document UTFT_Requirements.pdf.
+  There are no special requirements when using serial displays.
+
+  You can always find the latest version of the library at 
+  http://electronics.henningkarlsen.com/
+
+  If you make any modifications or improvements to the code, I would 
+  appreciate that you share the code with me so that I might include 
+  it in the next release. I can be contacted through 
+  http://electronics.henningkarlsen.com/contact.php.
+
+  This library is free software; you can redistribute it and/or
+  modify it under the terms of the GNU Lesser General Public
+  License as published by the Free Software Foundation; either
+  version 2.1 of the License, or (at your option) any later version.
+
+  This library is distributed in the hope that it will be useful,
+  but WITHOUT ANY WARRANTY; without even the implied warranty of
+  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+  Lesser General Public License for more details.
+
+  You should have received a copy of the GNU Lesser General Public
+  License along with this library; if not, write to the Free Software
+  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+*/
+
+#define UTFT_SPI_h
+
+#define UTFT_cbi(reg, bitmask) *reg &= ~bitmask
+#define UTFT_sbi(reg, bitmask) *reg |= bitmask
+
+#define cport(port, data) port &= data
+#define sport(port, data) port |= data
+
+#define swap(type, i, j) {type t = i; i = j; j = t;}
+
+#define fontbyte(x) cfont.font[x]  
+
+#define pgm_read_word(data) *data
+#define pgm_read_byte(data) *data
+#define bitmapdatatype unsigned short*
+
+#define regtype volatile uint32_t
+#define regsize uint32_t
+
+#define LEFT 0
+#define RIGHT 9999
+#define CENTER 9998
+
+#define PORTRAIT 0
+#define LANDSCAPE 1
+
+#define HX8347A         0
+#define ILI9327         1
+#define SSD1289         2
+#define ILI9325C        3
+#define ILI9325D_8      4
+#define ILI9325D_16     5
+#define HX8340B_8       6
+#define HX8340B_S       7
+#define HX8352A         8
+#define ST7735          9
+#define PCF8833         10
+#define S1D19122        11
+#define SSD1963_480     12
+#define SSD1963_800     13
+#define S6D1121_8       14
+#define S6D1121_16      15
+#define SSD1289LATCHED  16
+//#define NOT_IN_USE    17
+//#define NOT_IN_USE    18
+#define SSD1289_8       19
+#define SSD1963_800ALT  20
+#define ILI9481         21
+#define ILI9325D_16ALT  22
+#define S6D0164         23
+#define ST7735S         24
+#define ILI9341_S5P     25
+#define ILI9341_S4P     26
+#define R61581          27
+#define ILI9486         28
+#define CPLD            29
+#define HX8353C         30
+#define ST7735_ALT      31
+
+#define ITDB32          0   // HX8347-A (16bit)
+#define ITDB32WC        1   // ILI9327  (16bit)
+#define TFT01_32W       1   // ILI9327  (16bit)
+#define ITDB32S         2   // SSD1289  (16bit)
+#define TFT01_32        2   // SSD1289  (16bit)
+#define CTE32           2   // SSD1289  (16bit)
+#define ITDB24          3   // ILI9325C (8bit)
+#define ITDB24D         4   // ILI9325D (8bit)
+#define ITDB24DWOT      4   // ILI9325D (8bit)
+#define ITDB28          4   // ILI9325D (8bit)
+#define TFT01_24_8      4   // ILI9325D (8bit)
+#define DMTFT24104      4   // ILI9325D (8bit)
+#define DMTFT28103      4   // ILI9325D (8bit)
+#define TFT01_24_16     5   // ILI9325D (16bit)
+#define ITDB22          6   // HX8340-B (8bit)
+#define ITDB22SP        7   // HX8340-B (Serial 4Pin)
+#define ITDB32WD        8   // HX8352-A (16bit)
+#define TFT01_32WD      8   // HX8352-A (16bit)
+#define CTE32W          8   // HX8352-A (16bit)
+#define ITDB18SP        9   // ST7735   (Serial 5Pin)
+#define LPH9135         10  // PCF8833  (Serial 5Pin)
+#define ITDB25H         11  // S1D19122 (16bit)
+#define ITDB43          12  // SSD1963  (16bit) 480x272
+#define TFT01_43        12  // SSD1963  (16bit) 480x272
+#define ITDB50          13  // SSD1963  (16bit) 800x480
+#define TFT01_50        13  // SSD1963  (16bit) 800x480
+#define CTE50           13  // SSD1963  (16bit) 800x480
+#define EHOUSE50        13  // SSD1963  (16bit) 800x480
+#define ITDB24E_8       14  // S6D1121  (8bit)
+#define TFT01_24R2      14  // S6D1121  (8bit)
+#define ITDB24E_16      15  // S6D1121  (16bit)
+#define INFINIT32       16  // SSD1289  (Latched 16bit) -- Legacy, will be removed later
+#define ELEE32_REVA     16  // SSD1289  (Latched 16bit)
+//#define NOT_IN_USE    17  
+//#define NOT_IN_USE    18  
+#define ELEE32_REVB     19  // SSD1289  (8bit)
+#define TFT01_70        20  // SSD1963  (16bit) 800x480 Alternative Init
+#define CTE70           20  // SSD1963  (16bit) 800x480 Alternative Init
+#define EHOUSE70        20  // SSD1963  (16bit) 800x480 Alternative Init
+#define CTE32HR         21  // ILI9481  (16bit)
+#define CTE28           22  // ILI9325D (16bit) Alternative Init
+#define TFT01_28        22  // ILI9325D (16bit) Alternative Init
+#define CTE22           23  // S6D0164  (8bit)
+#define TFT01_22        23  // S6D0164  (8bit)
+#define DMTFT22102      23  // S6D0164  (8bit)
+#define TFT01_18SP      24  // ST7735S  (Serial 5Pin)
+#define TFT01_22SP      25  // ILI9341  (Serial 5Pin)
+#define TFT01_24SP      25  // ILI9341  (Serial 5Pin)
+#define TFT22SHLD       25  // ILI9341  (Serial 5Pin)
+#define DMTFT28105      25  // ILI9341  (Serial 5Pin)
+#define MI0283QT9       26  // ILI9341  (Serial 4Pin)
+#define CTE35IPS        27  // R61581   (16bit)
+#define CTE40           28  // ILI9486  (16bit)
+#define EHOUSE50CPLD    29  // CPLD     (16bit)
+#define CTE50CPLD       29  // CPLD     (16bit)
+#define CTE70CPLD       29  // CPLD     (16bit)
+#define DMTFT18101      30  // HX8353C  (Serial 5Pin)
+#define TFT18SHLD       31  // ST7735   (Serial 5Pin) Alternative Init
+
+#define SERIAL_4PIN     4
+#define SERIAL_5PIN     5
+#define LATCHED_16      17
+
+#define NOTINUSE        255
+
+//*********************************
+// COLORS
+//*********************************
+// VGA color palette
+#define VGA_BLACK       0x0000
+#define VGA_WHITE       0xFFFF
+#define VGA_RED         0xF800
+#define VGA_GREEN       0x0400
+#define VGA_BLUE        0x001F
+#define VGA_SILVER      0xC618
+#define VGA_GRAY        0x8410
+#define VGA_MAROON      0x8000
+#define VGA_YELLOW      0xFFE0
+#define VGA_OLIVE       0x8400
+#define VGA_LIME        0x07E0
+#define VGA_AQUA        0x07FF
+#define VGA_TEAL        0x0410
+#define VGA_NAVY        0x0010
+#define VGA_FUCHSIA     0xF81F
+#define VGA_PURPLE      0x8010
+#define VGA_TRANSPARENT 0xFFFFFFFF
+
+#define BMPIMAGEOFFSET 66
+    
+struct _current_font
+{
+    uint8_t* font;
+    uint8_t x_size;
+    uint8_t y_size;
+    uint8_t offset;
+    uint8_t numchars;
+};
+
+class ArduLCD
+{
+    public:
+        ArduLCD(PinName mosi, PinName miso, PinName sck, PinName cs);
+        void    InitLCD(uint8_t orientation=LANDSCAPE);
+        void    clrScr();
+        void    drawPixel(int x, int y);
+        void    drawLine(int x1, int y1, int x2, int y2);
+        void    fillScr(uint8_t r, uint8_t g, uint8_t b);
+        void    fillScr(uint16_t color);
+        void    drawRect(int x1, int y1, int x2, int y2);
+        void    drawRoundRect(int x1, int y1, int x2, int y2);
+        void    fillRect(int x1, int y1, int x2, int y2);
+        void    fillRoundRect(int x1, int y1, int x2, int y2);
+        void    drawCircle(int x, int y, int radius);
+        void    fillCircle(int x, int y, int radius);
+        void    setColor(uint8_t r, uint8_t g, uint8_t b);
+        void    setColor(uint16_t color);
+        uint16_t    getColor();
+        void    setBackColor(uint8_t r, uint8_t g, uint8_t b);
+        void    setBackColor(uint32_t color);
+        uint16_t    getBackColor();
+/*        void    printNumI(long num, int x, int y, int length=0, char filler=' ');
+        void    printNumF(double num, uint8_t dec, int x, int y, char divider='.', int length=0, char filler=' ');
+        void    setFont(uint8_t* font);
+        uint8_t* getFont();
+        uint8_t getFontXsize();
+        uint8_t getFontYsize();*/
+        void    drawBitmap(int x, int y, int sx, int sy, bitmapdatatype data, int scale=1);
+        void    drawBitmap(int x, int y, int sx, int sy, bitmapdatatype data, int deg, int rox, int roy);
+        int     getDisplayXSize();
+        int     getDisplayYSize();
+        
+        //***********not  use*****************
+        void    lcdOff();
+        void    lcdOn();
+        void    setContrast(char c);
+        void    setBrightness(uint8_t br);
+        void    setDisplayPage(uint8_t page);
+        void    setWritePage(uint8_t page);
+        //***********************************
+        
+        int bus_write(int address, int value);
+        uint8_t bus_read(int address);
+        
+        //void dispBitmap(File inFile);
+
+/*
+    The functions and variables below should not normally be used.
+    They have been left publicly available for use in add-on libraries
+*/
+        uint8_t            fch, fcl, bch, bcl;
+        uint8_t            orient;
+        uint8_t            model;
+        long            disp_x_size, disp_y_size;
+        uint8_t            display_model, display_transfer_mode, display_serial_mode;
+        regtype         *P_RS, *P_WR, *P_CS, *P_RST, *P_SDA, *P_SCL, *P_ALE;
+        regsize         B_RS, B_WR, B_CS, B_RST, B_SDA, B_SCL, B_ALE;
+        uint8_t            __p1, __p2, __p3, __p4, __p5;
+        _current_font   cfont;
+        bool         _transparent;
+
+        void LCD_Writ_Bus(char VH,char VL);
+        void LCD_Write_COM(char VL);
+        void LCD_Write_DATA(char VH,char VL);
+        void LCD_Write_COM_DATA(char com1,int dat1);
+        void setPixel(uint16_t color);
+        void drawHLine(int x, int y, int l);
+        void drawVLine(int x, int y, int l);
+//        void printChar(uint8_t c, int x, int y);
+        void setXY(uint16_t x1, uint16_t y1, uint16_t x2, uint16_t y2);
+        void clrXY();
+        void resetXY();
+//        void rotateChar(uint8_t c, int x, int y, int pos, int deg);
+        void _set_direction_registers(uint8_t mode);
+        void _fast_fill_16(int ch, int cl, long pix);
+        void _fast_fill_8(int ch, long pix);
+        void _convert_float(char *buf, double num, int width, uint8_t prec);
+        
+    protected:
+        SPI spi;                // does SPI MOSI, MISO and SCK        
+        DigitalOut _cs;         // does SPI CE
+};
+