Fork of Silabs MemoryLCD library

Dependents:   demoUI whrmDemoUI Host_Software_MAX32664GWEB_HR_EXTENDED Host_Software_MAX32664GWEC_SpO2_HR-_EXTE ... more

C++ library for Sharp Microelectronics 1.28 inch LCD TFT, LS013B7DH03, SPI bus. Forked from Silicon Labs MemoryLCD display driver.

Files at this revision

API Documentation at this revision

Comitter:
stevew817
Date:
Wed Aug 12 14:06:07 2015 +0000
Parent:
10:231fa7861d1f
Child:
12:ca0bcb4777e9
Commit message:
Implement Paul Staron's enhancements to the display driver classes, from https://developer.mbed.org/users/star297/code/MemoryLCD/rev/b64f87859c57

Changed in this revision

GraphicsDisplay.cpp Show annotated file Show diff for this revision Revisions of this file
GraphicsDisplay.h Show annotated file Show diff for this revision Revisions of this file
TextDisplay.cpp Show annotated file Show diff for this revision Revisions of this file
TextDisplay.h Show annotated file Show diff for this revision Revisions of this file
--- a/GraphicsDisplay.cpp	Wed Aug 12 13:32:01 2015 +0000
+++ b/GraphicsDisplay.cpp	Wed Aug 12 14:06:07 2015 +0000
@@ -5,6 +5,9 @@
  
 #include "GraphicsDisplay.h"
 
+#define incx() x++, dxt += d2xt, t += dxt
+#define incy() y--, dyt += d2yt, t += dyt
+
 const unsigned char FONT8x8[97][8] = {
 {0x08,0x08,0x08,0x00,0x00,0x00,0x00,0x00}, // columns, rows, num_bytes_per_char
 {0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}, // space 0x20
@@ -118,7 +121,47 @@
 }
     
 void GraphicsDisplay::character(int column, int row, int value) { 
-    blitbit(column * 8, row * 8, 8, 8, (char*)&(FONT8x8[value - 0x1F][0]));
+    if(externalfont){ // send external font
+        unsigned int hor,vert,offset,bpl,j,i,b;
+        const unsigned char* sign;
+        unsigned char z,w;
+        if ((value < 31) || (value > 127)) return;   // test char range
+        // read font parameter from start of array
+        offset = font[0];                    // bytes / char
+        hor = font[1];                       // get hor size of font
+        vert = font[2];                      // get vert size of font
+        bpl = font[3];                       // bytes per line
+        if (char_x + hor > width()) {
+            char_x = 0;
+            char_y = char_y + vert;
+            if (char_y >= height() - font[2]) {
+                char_y = 0;
+            }
+        }     
+        window(char_x, char_y,hor,vert); // char box
+        sign = &font[((value -32) * offset) + 4]; // start of char bitmap
+        w = sign[0];                          // width of actual char
+        for (j=0; j<vert; j++) {  //  vert line
+            for (i=0; i<hor; i++) {   //  horz line
+                z =  sign[bpl * i + ((j & 0xF8) >> 3)+1];
+                b = 1 << (j & 0x07);
+                if (( z & b ) == 0x00) {               
+                    putp(_foreground);              
+                } 
+                else {                     
+                    putp(_background);                                
+                }
+            }
+        }
+        if ((w + 2) < hor) {                   // x offset to next char
+            char_x += w + 2;
+            }
+            else char_x += hor;
+    }   
+    // send default font            
+    else {
+        blitbit(column * 8, row * 8, 8, 8, (char*)&(FONT8x8[value - 0x1F][0]));
+    }
 }
 
 void GraphicsDisplay::window(int x, int y, int w, int h) {
@@ -146,11 +189,38 @@
     }
 }
 
+void GraphicsDisplay::rect(int x0, int y0, int x1, int y1, int color) {
+    if (x1 > x0) hline(x0,x1,y0,color);
+    else  hline(x1,x0,y0,color);
+    if (y1 > y0) vline(x0,y0,y1,color);
+    else vline(x0,y1,y0,color);
+    if (x1 > x0) hline(x0,x1,y1,color);
+    else  hline(x1,x0,y1,color);
+    if (y1 > y0) vline(x1,y0,y1,color);
+    else vline(x1,y1,y0,color);
+    return;
+}
+ 
+void GraphicsDisplay::fillrect(int x0, int y0, int w, int h, int colour) {
+    unsigned long int index=0;
+    if (w < 0) {
+        x0 = x0 + w;
+        w = -w;
+    }
+    if (h < 0) {
+        y0 = y0 + h;
+        h = -h;
+    }
+    window(x0,y0,w,h);
+    int num = h*w;
+    for( index = 0; index<num; index++ ) {
+       putp(colour); 
+    }
+    return;
+}
+
 void GraphicsDisplay::fill(int x, int y, int w, int h, int colour) { 
-    window(x, y, w, h);
-    for(int i=0; i<w*h; i++) {
-        putp(colour);
-    }
+    fillrect(x, y, w, h, colour);
 }
 
 void GraphicsDisplay::circle(int x, int y, int r,int colour){
@@ -174,7 +244,187 @@
 	}
 
 }
-    
+
+// To draw circle set a and b to the same values
+void GraphicsDisplay::ellipse(int xc, int yc, int a, int b, unsigned int colour)
+{
+    /* e(x,y) = b^2*x^2 + a^2*y^2 - a^2*b^2 */
+    int x = 0, y = b;
+    long a2 = (long)a*a, b2 = (long)b*b;
+    long crit1 = -(a2/4 + a%2 + b2);
+    long crit2 = -(b2/4 + b%2 + a2);
+    long crit3 = -(b2/4 + b%2);
+    long t = -a2*y;                         // e(x+1/2,y-1/2) - (a^2+b^2)/4
+    long dxt = 2*b2*x, dyt = -2*a2*y;
+    long d2xt = 2*b2, d2yt = 2*a2;
+ 
+    while (y>=0 && x<=a) {
+        pixel(xc+x, yc+y, colour);
+        if (x!=0 || y!=0)
+            pixel(xc-x, yc-y, colour);
+        if (x!=0 && y!=0) {
+            pixel(xc+x, yc-y, colour);
+            pixel(xc-x, yc+y, colour);
+        }
+        if (t + b2*x <= crit1 ||            // e(x+1,y-1/2) <= 0
+                t + a2*y <= crit3)          // e(x+1/2,y) <= 0
+            incx();
+        else if (t - a2*y > crit2)          // e(x+1/2,y-1) > 0
+            incy();
+        else {
+            incx();
+            incy();
+        }
+    }
+}
+// To draw circle set a and b to the same values
+void GraphicsDisplay::fillellipse(int xc, int yc, int a, int b, unsigned int colour)
+{
+    /* e(x,y) = b^2*x^2 + a^2*y^2 - a^2*b^2 */
+    int x = 0, y = b;
+    int rx = x, ry = y;
+    unsigned int width = 1;
+    unsigned int height = 1;
+    long a2 = (long)a*a, b2 = (long)b*b;
+    long crit1 = -(a2/4 + a%2 + b2);
+    long crit2 = -(b2/4 + b%2 + a2);
+    long crit3 = -(b2/4 + b%2);
+    long t = -a2*y;                         // e(x+1/2,y-1/2) - (a^2+b^2)/4
+    long dxt = 2*b2*x, dyt = -2*a2*y;
+    long d2xt = 2*b2, d2yt = 2*a2;
+    if (b == 0) {
+        fillrect(xc-a, yc, 2*a+1, 1, colour);
+        return;
+    }
+    while (y>=0 && x<=a) {
+        if (t + b2*x <= crit1 ||            // e(x+1,y-1/2) <= 0
+                t + a2*y <= crit3) {        // e(x+1/2,y) <= 0
+            if (height == 1)
+                ;                           // draw nothing
+            else if (ry*2+1 > (height-1)*2) {
+                fillrect(xc-rx, yc-ry, width, height-1, colour);
+                fillrect(xc-rx, yc+ry+1, width, 1-height, colour);
+                ry -= height-1;
+                height = 1;
+            } else {
+                fillrect(xc-rx, yc-ry, width, ry*2+1, colour);
+                ry -= ry;
+                height = 1;
+            }
+            incx();
+            rx++;
+            width += 2;
+        } else if (t - a2*y > crit2) {      // e(x+1/2,y-1) > 0
+            incy();
+            height++;
+        } else {
+            if (ry*2+1 > height*2) {
+                fillrect(xc-rx, yc-ry, width, height, colour);
+                fillrect(xc-rx, yc+ry+1, width, -height, colour);
+            } else {
+                fillrect(xc-rx, yc-ry, width, ry*2+1, colour);
+            }
+            incx();
+            incy();
+            rx++;
+            width += 2;
+            ry -= height;
+            height = 1;
+        }
+    }
+    if (ry > height) {
+        fillrect(xc-rx, yc-ry, width, height, colour);
+        fillrect(xc-rx, yc+ry+1, width, -height, colour);
+    } else {
+        fillrect(xc-rx, yc-ry, width, ry*2+1, colour);
+    }
+}
+ 
+ 
+void GraphicsDisplay::line(int x0, int y0, int x1, int y1, int colour) {
+    //window(x0, y, w, h);
+    int   dx = 0, dy = 0;
+    int   dx_sym = 0, dy_sym = 0;
+    int   dx_x2 = 0, dy_x2 = 0;
+    int   di = 0;
+    dx = x1-x0;
+    dy = y1-y0;
+ 
+    if (dx == 0) {        /* vertical line */
+        if (y1 > y0) vline(x0,y0,y1,colour);
+        else vline(x0,y1,y0,colour);
+        return;
+    }
+    if (dx > 0) {
+        dx_sym = 1;
+    } else {
+        dx_sym = -1;
+    }
+    if (dy == 0) {        /* horizontal line */
+        if (x1 > x0) hline(x0,x1,y0,colour);
+        else  hline(x1,x0,y0,colour);
+        return;
+    }
+    if (dy > 0) {
+        dy_sym = 1;
+    } else {
+        dy_sym = -1;
+    }
+    dx = dx_sym*dx;
+    dy = dy_sym*dy;
+    dx_x2 = dx*2;
+    dy_x2 = dy*2;
+    if (dx >= dy) {
+        di = dy_x2 - dx;
+        while (x0 != x1) {
+ 
+            pixel(x0, y0, colour);
+            x0 += dx_sym;
+            if (di<0) {
+                di += dy_x2;
+            } else {
+                di += dy_x2 - dx_x2;
+                y0 += dy_sym;
+            }
+        }
+        pixel(x0, y0, colour);
+    } else {
+        di = dx_x2 - dy;
+        while (y0 != y1) {
+            pixel(x0, y0, colour);
+            y0 += dy_sym;
+            if (di < 0) {
+                di += dx_x2;
+            } else {
+                di += dx_x2 - dy_x2;
+                x0 += dx_sym;
+            }
+        }
+        pixel(x0, y0, colour);
+    }
+    return;
+}
+ 
+void GraphicsDisplay::hline(int x0, int x1, int y, int colour) {
+    int w;
+    w = x1 - x0 + 1;
+    window(x0,y,w,1);
+    for (int x=0; x<w; x++) {
+        putp(colour);
+    }
+    return;
+}
+ 
+void GraphicsDisplay::vline(int x, int y0, int y1, int colour) {
+    int h;
+    h = y1 - y0 + 1;
+    window(x,y0,1,h);
+    for (int y=0; y<h; y++) {
+        putp(colour);
+    }
+    return;
+}
+
 void GraphicsDisplay::cls() {
     fill(0, 0, width(), height(), _background);
 }
--- a/GraphicsDisplay.h	Wed Aug 12 13:32:01 2015 +0000
+++ b/GraphicsDisplay.h	Wed Aug 12 14:06:07 2015 +0000
@@ -30,8 +30,20 @@
     virtual void putp(int colour);
     
     virtual void cls();
+    virtual void rect(int x0, int y0, int x1, int y1, int colour);
+    virtual void fillrect(int x0, int y0, int w, int h, int colour);
+    // fill equals fillrect, name has been kept to not break compatibility
     virtual void fill(int x, int y, int w, int h, int colour);
+    
+    // To draw circle using ellipse, set a and b to the same values
+    virtual void ellipse(int xc, int yc, int a, int b, unsigned int colour);
+    virtual void fillellipse(int xc, int yc, int a, int b, unsigned int colour);
     virtual void circle(int x, int y, int r, int colour);
+    
+    virtual void hline(int x0, int x1, int y, int colour);
+    virtual void vline(int x0, int y0, int y1, int colour);
+    virtual void line(int x0, int y0, int x1, int y1, int colour);
+    
     virtual void blit(int x, int y, int w, int h, const int *colour);    
     virtual void blitbit(int x, int y, int w, int h, const char* colour);
     
--- a/TextDisplay.cpp	Wed Aug 12 13:32:01 2015 +0000
+++ b/TextDisplay.cpp	Wed Aug 12 14:06:07 2015 +0000
@@ -47,9 +47,23 @@
     }
 }
 
+void TextDisplay::set_font(const unsigned char * f) {
+    font = f;
+    if(font==NULL) {
+    	externalfont = 0;  // set display.font
+    	locate(0, 0);
+    }    
+    else{
+    	externalfont = 1;
+    	locate(0, 0);
+    }
+}
+
 void TextDisplay::locate(int column, int row) {
     _column = column;
     _row = row;
+    char_x = column;
+    char_y = row;
 }
 
 int TextDisplay::_getc() {
--- a/TextDisplay.h	Wed Aug 12 13:32:01 2015 +0000
+++ b/TextDisplay.h	Wed Aug 12 14:06:07 2015 +0000
@@ -47,12 +47,21 @@
     */
     virtual int columns() = 0;
     
+    // Sets external font usage, eg. dispaly.set_font(Arial12x12);
+    // This uses pixel positioning.
+    // display.set_font(NULL); returns to internal default font.
+    void set_font(const unsigned char * f);
+    
+    // set position of the next character or string print.
+    // External font, set pixel x(column),y(row) position.
+    // internal(default) font, set character column and row position 
+    virtual void locate(int column, int row);
+    
     // functions that come for free, but can be overwritten
 
     /** clear screen
     */
     virtual void cls();
-    virtual void locate(int column, int row);
     virtual void foreground(uint16_t colour);
     virtual void background(uint16_t colour);
     // putc (from Stream)
@@ -63,10 +72,16 @@
 
     virtual int _putc(int value);
     virtual int _getc();
-
+    
+    // external font functions
+    const unsigned char* font;
+    int externalfont;
+ 
     // character location
     uint16_t _column;
     uint16_t _row;
+    unsigned int char_x;
+    unsigned int char_y;
 
     // colours
     uint16_t _foreground;