Jurica Resetar / GDEP015OC1

Dependents:   acd52832_ePaper acd52832_SAADC_Differential_input_2 acd52832_SAADC_Differential_input_EPD acd52832_Car_battery_ch ... more

Fork of GDEP015OC1 by aconno dev team

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers GDEP015OC1.cpp Source File

GDEP015OC1.cpp

00001 /**
00002  *  Created by Filip Hormot (f.hormot@gmail.com) on 14/09/16.
00003  *  Edited by Jurica Resetar on 10/3/17.
00004  */
00005 #include "mbed.h"
00006 #include "GDEP015OC1.h"
00007 #include "5x7.h"
00008  
00009 #define EPD_WAIT_CONSTANT 100
00010  
00011 static const unsigned char _lutFull[] = { 
00012     0x02, 0x02, 0x01, 0x11, 0x12, 0x12, 0x22, 0x22, 0x66, 0x69, 0x69, 0x59, 0x58, 0x99, 0x99, 
00013     0x88, 0x00, 0x00, 0x00, 0x00, 0xF8, 0xB4, 0x13, 0x51, 0x35, 0x51, 0x51, 0x19, 0x01, 0x00
00014 };
00015  
00016 static const unsigned char _lutPart[] = {
00017     0x10, 0x18, 0x18, 0x08, 0x18, 0x18, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
00018     0x00, 0x00, 0x00, 0x00, 0x00, 0x13, 0x14, 0x44, 0x12, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
00019 };
00020  
00021 GDEP015OC1::GDEP015OC1(SPI& spi, PinName cs=p5, PinName dc=p6, PinName rst=p7, PinName busy=p8) : _spi(spi), _cs(cs), _dc(dc), _rst(rst), _busy(busy){
00022     _bold = true;
00023     _italic = false;
00024     _init();
00025 }
00026  
00027 void GDEP015OC1::_spiCommand(unsigned char command){
00028     _cs = _dc = 0;
00029     wait_us(1);
00030     _spi.write(command);
00031 }
00032  
00033 void GDEP015OC1::_spiData(unsigned char data){
00034     _cs = 0;
00035     _dc = 1;
00036     wait_us(1);
00037     _spi.write(data);
00038 }
00039  
00040 void GDEP015OC1::_init(void){
00041     _rst = _cs = 1;
00042     empty();    
00043 }
00044  
00045 void GDEP015OC1::_wakeUp(bool partial){
00046     _rst = 0;
00047     wait_ms(EPD_WAIT_CONSTANT);
00048     _rst = 1;
00049     wait_ms(EPD_WAIT_CONSTANT);
00050     
00051     //Stage 3
00052     //Driver Output control
00053     _spiCommand(0x01);
00054     _spiData(0xC7);     // (yDot-1)%256
00055     _spiData(0x00);     // (yDot-1)/256
00056     _spiData(0x00);     // 0x00
00057     
00058     //Softstart
00059     _spiCommand(0x0C);
00060     _spiData(0xD7);
00061     _spiData(0xD6);
00062     _spiData(0x9D);
00063  
00064     //VCOM setting
00065     _spiCommand(0x2C);
00066     _spiData(0xA8);
00067     
00068     //Dummy line period
00069     _spiCommand(0x3A);
00070     _spiData(0x1A);
00071     
00072     //Gate line width // 2us per line
00073     _spiCommand(0x3B);
00074     _spiData(0x08);
00075     
00076     //Set data entry mode
00077     _spiCommand(0x11);
00078     _spiData(0x01); //DO NOT TOUCH THIS! (MUST BE 0x01)
00079  
00080     //Define X display size
00081     _spiCommand(0x44);
00082     _spiData(0x00);
00083     _spiData(0x18);     //(xDot-1)/8
00084     //Define Y display size
00085     _spiCommand(0x45);
00086     _spiData(0xC7);     //(yDot-1)%256
00087     _spiData(0x00);     //(yDot-1)/256
00088     _spiData(0x00);     // Was 0x2B
00089     _spiData(0x00);     // Was 0x01
00090  
00091     //Define X RAM address
00092     _spiCommand(0x4E);
00093     _spiData(0x00);
00094     //Define Y RAM address
00095     _spiCommand(0x4F);
00096     _spiData(0xC7);
00097     _spiData(0x00);
00098  
00099     //Write LUT
00100     _spiCommand(0x32);
00101     if(partial){
00102         for(uint8_t i = 0; i<30;i++){
00103             _spiData(_lutPart[i]);
00104         }
00105     } else{
00106         for(uint8_t i = 0; i<30;i++){
00107             _spiData(_lutFull[i]);
00108         }
00109     }
00110 }
00111  
00112 void GDEP015OC1::_sleep(void){
00113     while(_busy == BUSY_STATE);
00114  
00115     _spiCommand(0x10);
00116     _spiData(0x01);
00117 }
00118  
00119 /*  
00120  *  If you touch this function satan will feast on your soul for an eternity!
00121  *  IM NOT PLAYING AROUND DONT FUCKING TOUCH IT!
00122  *  You are thinking about it...
00123  *  .
00124  *  .
00125  *  .
00126  *  DONT!
00127  */
00128 unsigned char GDEP015OC1::_pixelConv(unsigned char *data, int i){
00129     uint8_t pix = 0x00;
00130     for(uint8_t x = 0; x < 8; x++){
00131         pix |= ((*(data + (i*200)%5000 + (24-i/200) + x*25)>>((i/25)%8))&(0x01))<<(7-x);
00132     }
00133     return pix^0xFF;    
00134 }
00135  
00136 uint8_t GDEP015OC1::_mirrorData(uint8_t data){
00137     uint8_t mirror = 0x00;
00138     for(uint8_t i=0; i<8; i++)
00139         mirror |= ((data>>i) & 0x01) << (7 - i);
00140  
00141     return mirror;
00142 }
00143  
00144 void GDEP015OC1::fill(unsigned char data, int x){
00145     _buffer[x] = data;   
00146 }
00147  
00148 void GDEP015OC1::empty(void){
00149     for(uint16_t x=0; x<5000; x++)
00150         _buffer[x] = 0x00;
00151 }
00152  
00153 void GDEP015OC1::write(void){
00154     _wakeUp(true);
00155  
00156     _spiCommand(0x24);
00157     for(int16_t x=0; x>=0 && x<200; x++){
00158         for(int16_t y=24; y>=0 && y<25; y--){
00159             _spiData(_mirrorData(_pixelConv(_buffer, x*25+y)));
00160             wait_us(EPD_WAIT_CONSTANT);
00161         }
00162     }
00163  
00164     _spiCommand(0x22);
00165     _spiData(0x04);
00166     _spiCommand(0x22);
00167     _spiData(0x08);
00168  
00169     //Update
00170     _spiCommand(0x22);
00171     _spiData(0xC7);
00172     _spiCommand(0x20);
00173  
00174     _sleep();
00175 }
00176  
00177 void GDEP015OC1::writeFull(void){
00178     _wakeUp(false);
00179  
00180     _spiCommand(0x24);
00181     for(int16_t x=0; x>=0 && x<200; x++){
00182         for(int16_t y=24; y>=0 && y<25; y--){
00183             _spiData(_mirrorData(_pixelConv(_buffer, x*25+y)));
00184             wait_us(EPD_WAIT_CONSTANT);
00185         }
00186     }
00187  
00188     _spiCommand(0x22);
00189     _spiData(0x04);
00190     _spiCommand(0x22);
00191     _spiData(0x08);
00192  
00193     //Update
00194     _spiCommand(0x22);
00195     _spiData(0xC7);
00196     _spiCommand(0x20);
00197  
00198     _sleep();
00199 }
00200  
00201 void GDEP015OC1::drawPixel(uint16_t startX, uint16_t startY, bool color=0){
00202     if(startX>199 || startY>199) return;
00203     
00204     uint16_t i = startX/8 + startY*25;
00205  
00206     if(!color)
00207         _buffer[i] = (_buffer[i] | (1<<(7-startX%8)));
00208     else
00209         _buffer[i] = (_buffer[i] & (0xFF^(1<<(7-startX%8))));
00210 }
00211  
00212  
00213 void GDEP015OC1::drawLine(uint16_t startX,  uint16_t startY, uint16_t stopX, uint16_t stopY, bool color=0){
00214     int dx = abs(stopX-startX), sx = startX<stopX ? 1 : -1;
00215     int dy = abs(stopY-startY), sy = startY<stopY ? 1 : -1;
00216     int err = (dx>dy ? dx : -dy)/2, e2;
00217     
00218     for(;;){
00219         drawPixel(startX,startY,color);
00220         if (startX==stopX && startY==stopY) break;
00221         e2 = err;
00222         if (e2 >-dx) { err -= dy; startX += sx; }
00223         if (e2 < dy) { err += dx; startY += sy; }
00224     }
00225 }
00226  
00227 void GDEP015OC1::drawTriangle(uint16_t x1, uint16_t y1, uint16_t x2, uint16_t y2, uint16_t x3, uint16_t y3, bool color=0){
00228     drawLine(x1, y1, x2, y2, color);
00229     drawLine(x2, y2, x3, y3, color);
00230     drawLine(x3, y3, x1, y1, color);      
00231 }
00232  
00233 void GDEP015OC1::drawRectangle(uint16_t startX, uint16_t startY, uint16_t stopX, uint16_t stopY, bool color=0){
00234     drawLine(startX, startY, stopX,  startY, color);
00235     drawLine(stopX,  startY, stopX,  stopY,  color);
00236     drawLine(stopX,  stopY,  startX, stopY,  color);
00237     drawLine(startX, stopY,  startX, startY, color);    
00238 }
00239  
00240 void GDEP015OC1::drawCircle(uint16_t startX, uint16_t startY, uint16_t radius, bool color=0){
00241     int d,x,y;
00242  
00243     d=3-2*radius;
00244     x=0;
00245     y=radius;
00246     while(x<=y){
00247         drawPixel(startX+x,startY+y,color);
00248         drawPixel(startX-y,startY-x,color);
00249         drawPixel(startX+y,startY-x,color);
00250         drawPixel(startX-y,startY+x,color);
00251         drawPixel(startX+y,startY+x,color);
00252         drawPixel(startX-x,startY-y,color);
00253         drawPixel(startX+x,startY-y,color);
00254         drawPixel(startX-x,startY+y,color);
00255  
00256         if(d<=0)
00257             d=d+4*x+6;
00258         else{
00259             d=d+4*x-4*y+10;
00260             y--;
00261         }
00262         x++;
00263     }
00264 }
00265  
00266 void GDEP015OC1::fillCircle(uint16_t startX, uint16_t startY, uint16_t radius, bool color=0){
00267     for(uint16_t r = 1;r<=radius; r++){
00268         drawCircle(startX,   startY, r,   color);
00269         drawCircle(startX+1, startY, r-1, color);
00270         drawCircle(startX-1, startY, r-1, color);
00271     }
00272 }
00273  
00274 void GDEP015OC1::drawEllipse(uint16_t startX, uint16_t startY, uint16_t width, uint16_t height, bool color){
00275     int a2 = width*width;
00276     int b2 = height*height;
00277     int fa2 = 4*a2, fb2 = 4*b2;
00278     int x, y, sigma;
00279                                                         
00280   //First half                                                      
00281     for(int x = 0, y = height, sigma = 2*b2+a2*(1-2*height); b2*x <= a2*y; x++){
00282         drawPixel(startX+x,startY+y,color);
00283         drawPixel(startX-x,startY+y,color);
00284         drawPixel(startX+x,startY-y,color);
00285         drawPixel(startX-x,startY-y,color);
00286         if(sigma >= 0){
00287             sigma += fa2 * (1-y);
00288             y--;
00289         }
00290         sigma += b2 * ((4 * x) + 6);
00291     }
00292     //Second half
00293     for (x = width, y = 0, sigma = 2*a2+b2*(1-2*width); a2*y <= b2*x; y++){
00294         drawPixel(startX+x,startY+y,color);
00295         drawPixel(startX-x,startY+y,color);
00296         drawPixel(startX+x,startY-y,color);
00297         drawPixel(startX-x,startY-y,color);
00298         if (sigma >= 0){
00299                 sigma += fb2 * (1 - x);
00300                 x--;
00301         }
00302         sigma += a2 * ((4 * y) + 6);
00303     }       
00304 }
00305  
00306 void GDEP015OC1::fillEllipse(uint16_t startX, uint16_t startY, uint16_t width, uint16_t height, bool color=0){
00307     for(uint16_t w = width; w > 0; w--){
00308         drawEllipse(startX, startX, w, height, color);
00309     }
00310     drawLine(startX, startY-height, startX, startY+height, color);
00311 }
00312  
00313 void GDEP015OC1::writeChar(char character, uint16_t startX, uint16_t startY, bool color=0){
00314     unsigned char letter[FONT_WIDTH];
00315  
00316     //Grab data for the corresponding font
00317     for(uint8_t i = 0; i<FONT_WIDTH; i++)
00318         letter[i] = Font5x7[(character - ' ') * FONT_WIDTH + i];
00319  
00320     for(uint8_t i = 0; i<FONT_WIDTH; i++){
00321         for(uint8_t j = 0; j<FONT_HEIGHT; j++){
00322             if((letter[i]>>j)&0x01){
00323                 if(_italic){
00324                     drawPixel(startX+i+(FONT_HEIGHT/3 - j/3), startY+j, color);
00325                     if(_bold){
00326                         for(uint8_t z=0; z<2; z++)
00327                             drawPixel(startX+i-z+(FONT_HEIGHT/3- j/3), startY+j, color);
00328                     }
00329                 }
00330                 else{
00331                     drawPixel(startX+i, startY+j, color);
00332                     if(_bold){
00333                         for(uint8_t z=0; z<2; z++)
00334                             drawPixel(startX+i-z, startY+j, color);
00335                     }
00336                 }
00337             }
00338         }
00339     }   
00340 }
00341  
00342 void GDEP015OC1::writeString(char *string, uint16_t startX, uint16_t startY, bool color=0){
00343     uint8_t length = 0;
00344     while(*(string+length) != '\0') length++;
00345     
00346     for(uint8_t x=0; x<length; x++)
00347         writeChar(*(string+x), startX+(FONT_WIDTH+1)*x, startY, color); //FONT_WIDTH+1 gives a 1px space between the characters
00348 }