/*------------------------------------------------------------------------------ -- This file is a part of the libuc, microcontroler library -- Copyright (C) 2012, Alexis Jeandet -- -- This program is free software; you can redistribute it and/or modify -- it under the terms of the GNU General Public License as published by -- the Free Software Foundation; either version 3 of the License, or -- (at your option) any later version. -- -- This program 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 General Public License for more details. -- -- You should have received a copy of the GNU General Public License -- along with this program; if not, write to the Free Software -- Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA ------------------------------------------------------------------------------- -- Author : Alexis Jeandet -- Mail : alexis.jeandet@gmail.com -------------------------------------------------------------------------------*/ #include #include #include #include #include #ifdef __OPTIMIZED_MATH #include #endif #define _delay_(del) for(volatile int _d_e_l_=0;_d_e_l_<(del);_d_e_l_++); #define ilipaintLine(LCD,X,Y,W,buffer,buffsize) \ for(int l=0;l<1;l++)\ {\ ili9328setFrame(LCD,X,Y,W,1);\ int rem=(W)%buffsize;\ if(rem)LCD->interface->writeGRAM(buffer,rem);\ for(int i=rem;i<(W);i+=buffsize)\ {\ LCD->interface->writeGRAM(buffer,buffsize);\ }\ } void ili9328setGRAMaddress(LCD_t* LCD,uint16_t Haddress,uint16_t Vaddress) { LCD->interface->writereg(ILI9328_REGISTER_HORIZONTALGRAMADDRESSSET,Haddress); LCD->interface->writereg(ILI9328_REGISTER_VERTICALGRAMADDRESSSET,Vaddress); } void ili9328refreshenable(struct LCD_t* LCD,int enable) { if(enable) { //LCD->interface->writereg(ILI9328_REGISTER_ENTRYMODE,0x1018); } else { //LCD->interface->writereg(ILI9328_REGISTER_ENTRYMODE,0x1008); } } void ili9328setFrame(LCD_t* LCD,uint16_t X,uint16_t Y,uint16_t W,uint16_t H) { LCD->interface->writereg(ILI9328_REGISTER_HORIZONTALGRAMADDRESSSET,(uint32_t)X); LCD->interface->writereg(ILI9328_REGISTER_VERTICALGRAMADDRESSSET,(uint32_t)Y); LCD->interface->writereg(ILI9328_REGISTER_HORIZONTALADDRESSSTARTPOSITION,(uint32_t)X); LCD->interface->writereg(ILI9328_REGISTER_HORIZONTALADDRESSENDPOSITION,(uint32_t)(W+X-1)); LCD->interface->writereg(ILI9328_REGISTER_VERTICALADDRESSSTARTPOSITION,(uint32_t)Y); LCD->interface->writereg(ILI9328_REGISTER_VERTICALADDRESSENDPOSITION,(uint32_t)(Y+H-1)); } void ili9328paint(LCD_t* LCD,void* buffer,uint16_t Xpos,uint16_t Ypos,uint16_t Width,uint16_t Height) { if((LCD!=NULL) && (LCD->interface!=NULL) && (LCD->interface->writeGRAM!=NULL) && (LCD->width>(Xpos+Width)) && (LCD->height>(Ypos+Height))) { ili9328setFrame(LCD,Xpos,Ypos,Width,Height); LCD->interface->writeGRAM(buffer,Width*Height); } } void ili9328paintFilCircMidPoint(LCD_t* LCD,uint16_t Xpos,uint16_t Ypos,uint16_t r,uint32_t contColor,uint16_t contSz,uint32_t fillColor) { //Based on the mid point circle algorithm from Wikipedia //http://en.wikipedia.org/wiki/Midpoint_circle_algorithm if(contSzinterface->writeGRAM(tmp2,rem); for(int i=rem;i<(contSz2);i+=16) { LCD->interface->writeGRAM(tmp2,16); } W=2*Val1; if(W>(2*contSz2)) { W-=2*contSz2; rem=(W)%16; if(rem)LCD->interface->writeGRAM(tmp1,rem); for(int i=rem;i<(W);i+=16) { LCD->interface->writeGRAM(tmp1,16); } } rem=(contSz2)%16; if(rem)LCD->interface->writeGRAM(tmp2,rem); for(int i=rem;i<(contSz2);i+=16) { LCD->interface->writeGRAM(tmp2,16); } } } } void ili9328paintFilRect(LCD_t* LCD,uint16_t Xpos,uint16_t Ypos,uint16_t w,uint16_t h,uint32_t contColor,uint16_t contSz,uint32_t fillColor) { ili9328setFrame(LCD,Xpos,Ypos,w,h); uint16_t tmp[32]; for(int i=0;i<32;i++)tmp[i]=fillColor; for(int i=0;i<(h*w);i+=32) { LCD->interface->writeGRAM(tmp,32); } int rem=(w*h)%32; if(rem)LCD->interface->writeGRAM(tmp,rem); if(contSz) { ili9328setFrame(LCD,Xpos,Ypos,w,contSz); for(int i=0;i<32;i++)tmp[i]=contColor; rem=(w*contSz)%32; if(rem)LCD->interface->writeGRAM(tmp,rem); for(int i=rem;i<(w*contSz);i+=32) { LCD->interface->writeGRAM(tmp,32); } ili9328setFrame(LCD,Xpos,Ypos+h-contSz,w,contSz); rem=(w*contSz)%32; if(rem)LCD->interface->writeGRAM(tmp,rem); for(int i=rem;i<(w*contSz);i+=32) { LCD->interface->writeGRAM(tmp,32); } ili9328setFrame(LCD,Xpos,Ypos,contSz,h); rem=(h*contSz)%32; if(rem)LCD->interface->writeGRAM(tmp,rem); for(int i=rem;i<(h*contSz);i+=32) { LCD->interface->writeGRAM(tmp,32); } ili9328setFrame(LCD,Xpos+w-contSz,Ypos,contSz,h); rem=(h*contSz)%32; if(rem)LCD->interface->writeGRAM(tmp,rem); for(int i=rem;i<(h*contSz);i+=32) { LCD->interface->writeGRAM(tmp,32); } } } void ili9328paintText(LCD_t* LCD,char* buffer,uint16_t Xpos,uint16_t Ypos,sFONT* font,uint32_t color) { int w=font->Width,h=font->Height,bpl=font->bytesPerLine,pix=0,tableoffset=0; uint16_t tmp[w]; uint16_t linenum=0,charnum=0; uint8_t line=0; while(*buffer) { ili9328setFrame(LCD,Xpos+(charnum*w),Ypos-h,w,1); LCD->interface->readGRAM(tmp,w); for(int i=0;i<(h*w);i++) { if( ((i%w)==0) ) //read current line to apply text pixmap { if(linenum++>0) { ili9328setFrame(LCD,Xpos+(charnum*w),Ypos + linenum -h,w,1); LCD->interface->writeGRAM(tmp,w); ili9328setFrame(LCD,Xpos+(charnum*w),Ypos + linenum + 1-h,w,1); LCD->interface->readGRAM(tmp,w); pix=0; } } if((pix%8) == 0) { line=font->table[(((*buffer)-32)*h*bpl)+tableoffset++]; } if((line & (uint8_t)0x01)==(uint8_t)1)tmp[pix]=(uint16_t)color; pix++; line>>=1; } linenum=0; tableoffset=0; charnum++; buffer++; } } int ili9328init(struct LCD_t* LCD) { if((LCD!=NULL) && (LCD->interface!=NULL) && (LCD->interface->writereg!=NULL)) { LCD->interface->writereg(ILI9328_REGISTER_DRIVEROUTPUTCONTROL1, 0x0100); // Driver Output Control Register (R01h) LCD->interface->writereg(ILI9328_REGISTER_LCDDRIVINGCONTROL, 0x0700); // LCD Driving Waveform Control (R02h) LCD->interface->writereg(ILI9328_REGISTER_ENTRYMODE, 0x1030); // Entry Mode (R03h) LCD->interface->writereg(ILI9328_REGISTER_DISPLAYCONTROL2, 0x0202); LCD->interface->writereg(ILI9328_REGISTER_DISPLAYCONTROL3, 0x0000); LCD->interface->writereg(ILI9328_REGISTER_DISPLAYCONTROL4, 0x0000); // Fmark On LCD->interface->writereg(ILI9328_REGISTER_POWERCONTROL1, 0x0000); // Power Control 1 (R10h) LCD->interface->writereg(ILI9328_REGISTER_POWERCONTROL2, 0x0007); // Power Control 2 (R11h) LCD->interface->writereg(ILI9328_REGISTER_POWERCONTROL3, 0x0000); // Power Control 3 (R12h) LCD->interface->writereg(ILI9328_REGISTER_POWERCONTROL4, 0x0000); // Power Control 4 (R13h) delay_100us(10); LCD->interface->writereg(ILI9328_REGISTER_POWERCONTROL1, 0x14B0); // Power Control 1 (R10h) delay_100us(10); LCD->interface->writereg(ILI9328_REGISTER_POWERCONTROL2, 0x0007); // Power Control 2 (R11h) delay_100us(10); LCD->interface->writereg(ILI9328_REGISTER_POWERCONTROL3, 0x008E); // Power Control 3 (R12h) LCD->interface->writereg(ILI9328_REGISTER_POWERCONTROL4, 0x0C00); // Power Control 4 (R13h) LCD->interface->writereg(ILI9328_REGISTER_POWERCONTROL7, 0x0015); // NVM read data 2 (R29h) delay_100us(500); LCD->interface->writereg(ILI9328_REGISTER_GAMMACONTROL1, 0x0000); // Gamma Control 1 LCD->interface->writereg(ILI9328_REGISTER_GAMMACONTROL2, 0x0107); // Gamma Control 2 LCD->interface->writereg(ILI9328_REGISTER_GAMMACONTROL3, 0x0000); // Gamma Control 3 LCD->interface->writereg(ILI9328_REGISTER_GAMMACONTROL4, 0x0203); // Gamma Control 4 LCD->interface->writereg(ILI9328_REGISTER_GAMMACONTROL5, 0x0402); // Gamma Control 5 LCD->interface->writereg(ILI9328_REGISTER_GAMMACONTROL6, 0x0000); // Gamma Control 6 LCD->interface->writereg(ILI9328_REGISTER_GAMMACONTROL7, 0x0207); // Gamma Control 7 LCD->interface->writereg(ILI9328_REGISTER_GAMMACONTROL8, 0x0000); // Gamma Control 8 LCD->interface->writereg(ILI9328_REGISTER_GAMMACONTROL9, 0x0203); // Gamma Control 9 LCD->interface->writereg(ILI9328_REGISTER_GAMMACONTROL10, 0x0403); // Gamma Control 10 LCD->interface->writereg(ILI9328_REGISTER_HORIZONTALADDRESSSTARTPOSITION, 0x0000); // Window Horizontal RAM Address Start (R50h) LCD->interface->writereg(ILI9328_REGISTER_HORIZONTALADDRESSENDPOSITION, 240 - 1); // Window Horizontal RAM Address End (R51h) LCD->interface->writereg(ILI9328_REGISTER_VERTICALADDRESSSTARTPOSITION, 0X0000); // Window Vertical RAM Address Start (R52h) LCD->interface->writereg(ILI9328_REGISTER_VERTICALADDRESSENDPOSITION, 320 - 1); // Window Vertical RAM Address End (R53h) LCD->interface->writereg(ILI9328_REGISTER_DRIVEROUTPUTCONTROL2, 0xa700); // Driver Output Control (R60h) LCD->interface->writereg(ILI9328_REGISTER_BASEIMAGEDISPLAYCONTROL, 0x0003); // Driver Output Control (R61h) - enable VLE LCD->interface->writereg(ILI9328_REGISTER_PANELINTERFACECONTROL1, 0X0010); // Panel Interface Control 1 (R90h) // Display On LCD->interface->writereg(ILI9328_REGISTER_DISPLAYCONTROL1, 0x0133); // Display Control (R07h) delay_100us(500); LCD->interface->writereg(ILI9328_REGISTER_ENTRYMODE, 0x0038); } return 0; }