diff --git a/TFT_ILI9163C.cpp b/TFT_ILI9163C.cpp index 5ae0ef9..e832508 100644 --- a/TFT_ILI9163C.cpp +++ b/TFT_ILI9163C.cpp @@ -117,6 +117,7 @@ void TFT_ILI9163C::setBitrate(uint32_t n){ void TFT_ILI9163C::begin(void) { + sleep = 0; #ifdef __AVR__ pinMode(_rs, OUTPUT); pinMode(_cs, OUTPUT); @@ -267,16 +268,25 @@ void TFT_ILI9163C::chipInit() { delay(1); writecommand_cont(CMD_CLMADRS);//Set Column Address + /* writedata8_cont(0x00); writedata8_cont(0X00); writedata8_cont(0X00); writedata8_cont(_GRAMWIDTH); + */ + writedata16_cont(0x00); + writedata16_cont(_GRAMWIDTH); writecommand_cont(CMD_PGEADRS);//Set Page Address + /* writedata8_cont(0x00); writedata8_cont(0X00); writedata8_cont(0X00); - writedata8_last(_GRAMHEIGH); + writedata8_last(_GRAMHEIGH); + */ + writedata16_cont(0x00); + writedata16_last(_GRAMHEIGH); + SPI.endTransaction(); colorSpace(_colorspaceData); setRotation(0); @@ -338,16 +348,20 @@ void TFT_ILI9163C::chipInit() { delay(1); writecommand(CMD_CLMADRS);//Set Column Address - writedata(0x00); - writedata(0X00); - writedata(0X00); - writedata(_GRAMWIDTH); + //writedata(0x00); + //writedata(0X00); + //writedata(0X00); + //writedata(_GRAMWIDTH); + writedata16(0x00); + writedata16(_GRAMWIDTH); writecommand(CMD_PGEADRS);//Set Page Address - writedata(0x00); - writedata(0X00); - writedata(0X00); - writedata(_GRAMHEIGH); + //writedata(0x00); + //writedata(0X00); + //writedata(0X00); + //writedata(_GRAMHEIGH); + writedata16(0X00); + writedata16(_GRAMHEIGH) colorSpace(_colorspaceData); setRotation(0); @@ -373,46 +387,139 @@ void TFT_ILI9163C::colorSpace(uint8_t cspace) { } } +void TFT_ILI9163C::invertDisplay(boolean i) { + #if defined(__MK20DX128__) || defined(__MK20DX256__) + SPI.beginTransaction(SPISettings(SPICLOCK, MSBFIRST, SPI_MODE0)); + writecommand_last(i ? CMD_DINVON : CMD_DINVOF); + SPI.endTransaction(); + #else + writecommand(i ? CMD_DINVON : CMD_DINVOF); + #endif +} +void TFT_ILI9163C::display(boolean onOff) { + if (onOff){ + #if defined(__MK20DX128__) || defined(__MK20DX256__) + SPI.beginTransaction(SPISettings(SPICLOCK, MSBFIRST, SPI_MODE0)); + writecommand_last(CMD_DISPON); + endProc(); + #else + writecommand(CMD_DISPON); + #endif + } else { + #if defined(__MK20DX128__) || defined(__MK20DX256__) + SPI.beginTransaction(SPISettings(SPICLOCK, MSBFIRST, SPI_MODE0)); + writecommand_last(CMD_DISPOFF); + endProc(); + #else + writecommand(CMD_DISPOFF); + #endif + } +} + +void TFT_ILI9163C::sleepMode(boolean mode) { + if (mode){ + if (sleep == 1) return;//already sleeping + sleep = 1; + #if defined(__MK20DX128__) || defined(__MK20DX256__) + SPI.beginTransaction(SPISettings(SPICLOCK, MSBFIRST, SPI_MODE0)); + writecommand_last(CMD_SLPIN); + endProc(); + #else + writecommand(CMD_SLPIN); + #endif + delay(5);//needed + } else { + if (sleep == 0) return; //Already awake + sleep = 0; + #if defined(__MK20DX128__) || defined(__MK20DX256__) + SPI.beginTransaction(SPISettings(SPICLOCK, MSBFIRST, SPI_MODE0)); + writecommand_last(CMD_SLPOUT); + endProc(); + #else + writecommand(CMD_SLPOUT); + #endif + delay(120);//needed + } +} + +/* +void TFT_ILI9163C::defineScrollArea(uint16_t a,uint16_t c){ + //0,2 + uint16_t b; + if ((a+c) > _TFTWIDTH) return; + b = (_TFTWIDTH - (a+c)); + SPI.beginTransaction(SPISettings(SPICLOCK, MSBFIRST, SPI_MODE0)); + writecommand_cont(0x33); + if (rotation == 0 || rotation > 1){ + writedata16_cont(a); + writedata16_cont(b); + writedata16_last(c); + } else { + writedata16_cont(a + __OFFSET); + writedata16_cont(b + __OFFSET); + writedata16_last(c + __OFFSET); + } + endProc(); + setAddr(0x00,0x00,_GRAMWIDTH-1,_GRAMHEIGH-1); + setRotation(0); + +} +*/ + +void TFT_ILI9163C::scroll(uint16_t adrs) { + SPI.beginTransaction(SPISettings(SPICLOCK, MSBFIRST, SPI_MODE0)); + writecommand_cont(CMD_VSSTADRS); + writedata16_last(adrs); + endProc(); +} + + +//corrected! void TFT_ILI9163C::clearScreen(uint16_t color) { int px; - setAddr(0x00,0x00,_GRAMWIDTH-1,_GRAMHEIGH-1); #if defined(__MK20DX128__) || defined(__MK20DX256__) - for (px = 0;px < _GRAMSIZE-1; px++){ + SPI.beginTransaction(SPISettings(SPICLOCK, MSBFIRST, SPI_MODE0)); + writecommand_cont(CMD_RAMWR);//this was missed! + for (px = 0;px < _GRAMSIZE; px++){ writedata16_cont(color); } - writedata16_last(color); + _setAddrWindow(0x00,0x00,_GRAMWIDTH,_GRAMHEIGH);//go home + writecommand_last(CMD_NOP); endProc(); #else + writecommand(CMD_RAMWR); for (px = 0;px < _GRAMSIZE; px++){ writedata16(color); } + setAddr(0x00,0x00,_GRAMWIDTH,_GRAMHEIGH);//go home #endif - } void TFT_ILI9163C::writeScreen(const uint32_t *bitmap) { uint16_t color; int px; - setAddr(0x00,0x00,_GRAMWIDTH-1,_GRAMHEIGH-1); #if defined(__MK20DX128__) || defined(__MK20DX256__) - for (px = 0;px < 16383; px++){ + writecommand_cont(CMD_RAMWR); + for (px = 0;px < 16384; px++){ color = Color24To565(bitmap[px]); writedata16_cont(color); } - color = Color24To565(bitmap[16383]); - writedata16_last(color); + _setAddrWindow(0x00,0x00,_GRAMWIDTH,_GRAMHEIGH); endProc(); #else - for (px = 0;px < 16384; px++){ - color = Color24To565(bitmap[px]); - writedata16(color); - } + writecommand(CMD_RAMWR); + for (px = 0;px < 16384; px++){ + color = Color24To565(bitmap[px]); + writedata16(color); + } + setAddr(0x00,0x00,_GRAMWIDTH,_GRAMHEIGH); #endif } void TFT_ILI9163C::homeAddress() { - setAddrWindow(0x00,0x00,_GRAMWIDTH-1,_GRAMHEIGH-1); + //setAddrWindow(0x00,0x00,_GRAMWIDTH-1,_GRAMHEIGH-1); + setAddrWindow(0x00,0x00,_GRAMWIDTH,_GRAMHEIGH); } @@ -441,7 +548,6 @@ void TFT_ILI9163C::drawPixel(int16_t x, int16_t y, uint16_t color) { if ((x < 0) || (y < 0)) return; setAddr(x,y,x+1,y+1); #if defined(__MK20DX128__) || defined(__MK20DX256__) - //writecommand_cont(CMD_RAMWR);//not needed writedata16_last(color); endProc(); #else @@ -648,30 +754,18 @@ void TFT_ILI9163C::setAddrWindow(uint16_t x0, uint16_t y0, uint16_t x1, uint16_t SPI.endTransaction(); #else writecommand(CMD_CLMADRS); // Column - if (rotation == 0){ - writedata16(x0); - writedata16(x1); - } else if (rotation == 1){ - writedata16(x0 + __OFFSET); - writedata16(x1 + __OFFSET); - } else if (rotation == 2){ + if (rotation == 0 || rotation > 1){ writedata16(x0); writedata16(x1); } else { - writedata16(x0); - writedata16(x1); + writedata16(x0 + __OFFSET); + writedata16(x1 + __OFFSET); } writecommand(CMD_PGEADRS); // Page if (rotation == 0){ writedata16(y0 + __OFFSET); writedata16(y1 + __OFFSET); - } else if (rotation == 1){ - writedata16(y0); - writedata16(y1); - } else if (rotation == 2){ - writedata16(y0); - writedata16(y1); } else { writedata16(y0); writedata16(y1); @@ -683,30 +777,18 @@ void TFT_ILI9163C::setAddrWindow(uint16_t x0, uint16_t y0, uint16_t x1, uint16_t #if defined(__MK20DX128__) || defined(__MK20DX256__) void TFT_ILI9163C::_setAddrWindow(uint16_t x0, uint16_t y0, uint16_t x1, uint16_t y1) { writecommand_cont(CMD_CLMADRS); // Column - if (rotation == 0){ - writedata16_cont(x0); - writedata16_cont(x1); - } else if (rotation == 1){ - writedata16_cont(x0 + __OFFSET); - writedata16_cont(x1 + __OFFSET); - } else if (rotation == 2){ + if (rotation == 0 || rotation > 1){ writedata16_cont(x0); writedata16_cont(x1); } else { - writedata16_cont(x0); - writedata16_cont(x1); + writedata16_cont(x0 + __OFFSET); + writedata16_cont(x1 + __OFFSET); } writecommand_cont(CMD_PGEADRS); // Page if (rotation == 0){ writedata16_cont(y0 + __OFFSET); writedata16_cont(y1 + __OFFSET); - } else if (rotation == 1){ - writedata16_cont(y0); - writedata16_cont(y1); - } else if (rotation == 2){ - writedata16_cont(y0); - writedata16_cont(y1); } else { writedata16_cont(y0); writedata16_cont(y1); @@ -752,13 +834,5 @@ void TFT_ILI9163C::setRotation(uint8_t m) { } -void TFT_ILI9163C::invertDisplay(boolean i) { - #if defined(__MK20DX128__) || defined(__MK20DX256__) - SPI.beginTransaction(SPISettings(SPICLOCK, MSBFIRST, SPI_MODE0)); - writecommand_last(i ? CMD_DINVON : CMD_DINVOF); - SPI.endTransaction(); - #else - writecommand(i ? CMD_DINVON : CMD_DINVOF); - #endif -} + diff --git a/TFT_ILI9163C.h b/TFT_ILI9163C.h index 5556903..dab2f0e 100644 --- a/TFT_ILI9163C.h +++ b/TFT_ILI9163C.h @@ -71,14 +71,16 @@ 0.3b1: Complete rework on Teensy SPI based on Paul Stoffregen work SPI transaction,added BLACK TAG 2.2 display 0.3b2: Minor fix, load 24bit image, Added conversion utility - 0.4:some improvement, new ballistic gauge example! + 0.4: some improvement, new ballistic gauge example! + 0.5: Added scroll and more commands, optimizations + Fixed a nasty bug in fill screen! +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ BugList of the current version: - - Actually no scroll commands (only in release will be included). + Please report any! -Here's the speed test between 0.2b5 and 0.3b1 on Teensy3.1 +Here's the speed test between 0.2b5 and 0.3b1 on Teensy3.1 (major SPI changes) ------------------------------------------------------------------------ Lines 17024 16115 BETTER Horiz/Vert Lines 5360 5080 BETTER @@ -137,7 +139,7 @@ you can copy those parameters and create setup for different displays. #define _TFTWIDTH 128//the REAL W resolution of the TFT #define _TFTHEIGHT 128//the REAL H resolution of the TFT #define _GRAMWIDTH 128 - #define _GRAMHEIGH 128//160 + #define _GRAMHEIGH 160//160 #define _GRAMSIZE _GRAMWIDTH * _GRAMHEIGH//*see note 1 #define __COLORSPC 1// 1:GBR - 0:RGB #define __GAMMASET3 //uncomment for another gamma @@ -213,7 +215,7 @@ Not tested! #define CMD_TEFXLON 0x35//Tearing Effect Line ON #define CMD_TEFXLOF 0x34//Tearing Effect Line OFF #define CMD_MADCTL 0x36//Memory Access Control - +#define CMD_VSSTADRS 0x37//Vertical Scrolling Start address #define CMD_PIXFMT 0x3A//Interface Pixel Format #define CMD_FRMCTR1 0xB1//Frame Rate Control (In normal mode/Full colors) #define CMD_FRMCTR2 0xB2//Frame Rate Control(In Idle mode/8-colors) @@ -237,7 +239,6 @@ Not tested! #define CMD_GAMRSEL 0xF2//GAM_R_SEL - class TFT_ILI9163C : public Adafruit_GFX { public: @@ -261,18 +262,23 @@ class TFT_ILI9163C : public Adafruit_GFX { fillRect(int16_t x, int16_t y, int16_t w, int16_t h,uint16_t color), setRotation(uint8_t r), invertDisplay(boolean i); + void display(boolean onOff); + void sleepMode(boolean mode); + //void defineScrollArea(uint16_t a,uint16_t c); + void scroll(uint16_t adrs); void writeScreen(const uint32_t *bitmap); - uint16_t Color565(uint8_t r, uint8_t g, uint8_t b); + uint16_t Color565(uint8_t r, uint8_t g, uint8_t b); //convert 24bit color into packet 16 bit one (credits for this are all mine) inline uint16_t Color24To565(int32_t color_) { return ((((color_ >> 16) & 0xFF) / 8) << 11) | ((((color_ >> 8) & 0xFF) / 4) << 5) | (((color_) & 0xFF) / 8);} - void setBitrate(uint32_t n); + void setBitrate(uint32_t n); private: uint8_t _Mactrl_Data;//container for the memory access control data uint8_t _colorspaceData; void colorSpace(uint8_t cspace); - void setAddr(uint16_t x0, uint16_t y0, uint16_t x1, uint16_t y1); - void endProc(void); + void setAddr(uint16_t x0, uint16_t y0, uint16_t x1, uint16_t y1); + void endProc(void); + uint8_t sleep; #if defined(__MK20DX128__) || defined(__MK20DX256__) // #else diff --git a/examples/display_command/display_command.ino b/examples/display_command/display_command.ino new file mode 100644 index 0000000..279b113 --- /dev/null +++ b/examples/display_command/display_command.ino @@ -0,0 +1,51 @@ +/* +Turn display ON/OFF - this command it's almost unusable since it doesn't control the backligh +It result in a white screen! +*/ + + +#include +#include +#include + +// Color definitions +#define BLACK 0x0000 +#define BLUE 0x001F +#define RED 0xF800 +#define GREEN 0x07E0 +#define CYAN 0x07FF +#define MAGENTA 0xF81F +#define YELLOW 0xFFE0 +#define WHITE 0xFFFF + +/* +Teensy3.x and Arduino's + You are using 4 wire SPI here, so: + MOSI: 11//Teensy3.x/Arduino UNO (for MEGA/DUE refere to arduino site) + MISO: 12//Teensy3.x/Arduino UNO (for MEGA/DUE refere to arduino site) + SCK: 13//Teensy3.x/Arduino UNO (for MEGA/DUE refere to arduino site) + the rest of pin below: + */ +#define __CS 10 +#define __DC 9 +/* +Teensy 3.x can use: 2,6,9,10,15,20,21,22,23 + Arduino's 8 bit: any + DUE: check arduino site + If you do not use reset, tie it to +3V3 + */ + + +TFT_ILI9163C tft = TFT_ILI9163C(__CS, __DC); + +void setup() { + tft.begin(); + tft.fillScreen(0xF81F); +} + +void loop(void) { + tft.display(false); + delay(1000); + tft.display(true); + delay(1000); +} diff --git a/examples/easyScroll/easyScroll.ino b/examples/easyScroll/easyScroll.ino new file mode 100644 index 0000000..474b6f5 --- /dev/null +++ b/examples/easyScroll/easyScroll.ino @@ -0,0 +1,96 @@ +/* +Rudimentary scroll! + */ + + +#include +#include +#include + +// Color definitions +#define BLACK 0x0000 +#define BLUE 0x001F +#define RED 0xF800 +#define GREEN 0x07E0 +#define CYAN 0x07FF +#define MAGENTA 0xF81F +#define YELLOW 0xFFE0 +#define WHITE 0xFFFF + +/* +Teensy3.x and Arduino's + You are using 4 wire SPI here, so: + MOSI: 11//Teensy3.x/Arduino UNO (for MEGA/DUE refere to arduino site) + MISO: 12//Teensy3.x/Arduino UNO (for MEGA/DUE refere to arduino site) + SCK: 13//Teensy3.x/Arduino UNO (for MEGA/DUE refere to arduino site) + the rest of pin below: + */ +#define __CS 10 +#define __DC 9 +/* +Teensy 3.x can use: 2,6,9,10,15,20,21,22,23 + Arduino's 8 bit: any + DUE: check arduino site + If you do not use reset, tie it to +3V3 + */ + + +TFT_ILI9163C tft = TFT_ILI9163C(__CS, __DC); + +void setup() { + tft.begin(); + tft.setRotation(0); + tft.setCursor(0, 0); + tft.setTextColor(WHITE); + tft.setTextSize(1); + tft.println("Hello World!"); + tft.setTextColor(YELLOW); + tft.setTextSize(2); + tft.println(1234.56); + tft.setTextColor(RED); + tft.setTextSize(3); + tft.println(0xDEAD, HEX); + tft.println(); + tft.setTextColor(GREEN); + tft.setTextSize(4); + tft.println("Hello"); + tft.setTextSize(2); + tft.println("I implore thee,"); + tft.setTextSize(1); + tft.println("my foonting turlingdromes."); + tft.println("And hooptiously drangle me"); + tft.println("with crinkly bindlewurdles,"); + tft.println("Or I will rend thee"); + tft.println("in the gobberwarts"); + tft.println("with my blurglecruncheon,"); + tft.println("see if I don't!"); +} + + +int t = 0; + + +void loop(void) { + tft.scroll(t); + if (t > 160) { + t = 0; + } + else { + t++; + } + + delay(10); +} + + +void testFilledRects() { + int n, i, i2, + cx = (tft.width() / 2), + cy = (tft.height() / 2); + n = min(tft.width(), tft.height()); + for(i=n; i>0; i-=6) { + i2 = i / 2; + tft.fillRect(cx-i2, cy-i2, i, i, random(0x0000,0xFFFF)); + tft.drawRect(cx-i2, cy-i2, i, i, random(0x0000,0xFFFF)); + } +} diff --git a/examples/sleep/sleep.ino b/examples/sleep/sleep.ino new file mode 100644 index 0000000..c9802b1 --- /dev/null +++ b/examples/sleep/sleep.ino @@ -0,0 +1,55 @@ +/* +Sleep Command example +Very simple, when sleep on DC/DC converter is stopped, Internal oscillator is stopped, and panel scanning is stopped +MCU interface and memory are still working and the memory keeps its contents. +NOTE: +The led background still active since it's NOT controlled by chip so the result it's a white screen until you turn off +the backlight! +*/ + +#include +#include +#include + +// Color definitions +#define BLACK 0x0000 +#define BLUE 0x001F +#define RED 0xF800 +#define GREEN 0x07E0 +#define CYAN 0x07FF +#define MAGENTA 0xF81F +#define YELLOW 0xFFE0 +#define WHITE 0xFFFF + +/* +Teensy3.x and Arduino's + You are using 4 wire SPI here, so: + MOSI: 11//Teensy3.x/Arduino UNO (for MEGA/DUE refere to arduino site) + MISO: 12//Teensy3.x/Arduino UNO (for MEGA/DUE refere to arduino site) + SCK: 13//Teensy3.x/Arduino UNO (for MEGA/DUE refere to arduino site) + the rest of pin below: + */ +#define __CS 10 +#define __DC 9 +/* +Teensy 3.x can use: 2,6,9,10,15,20,21,22,23 + Arduino's 8 bit: any + DUE: check arduino site + If you do not use reset, tie it to +3V3 + */ + + +TFT_ILI9163C tft = TFT_ILI9163C(__CS, __DC); + +void setup() { + tft.begin(); + tft.fillScreen(0xF800); + delay(500); +} + +void loop(void) { + tft.sleepMode(true); + delay(1000); + tft.sleepMode(false); + delay(1000); +} diff --git a/keywords.txt b/keywords.txt index 23d23ea..6b7b4f9 100644 --- a/keywords.txt +++ b/keywords.txt @@ -9,5 +9,8 @@ setBitrate KEYWORD2 clearScreen KEYWORD2 writeScreen KEYWORD2 Color24To565 KEYWORD2 +sleepMode KEYWORD2 +display KEYWORD2 +writeScreen KEYWORD2