Lib for the new LCD Display with ILI9341 controller

Dependents:   TFT_Test_ILI9341 touch_piirto TFT_banggood TFT_Test_ILI9341-a-fish ... more

Lib for 320*240 Pixel Color LCD with ILI9341 controller. Based on MI0283QT-9 datasheet. The lib is based on the http://mbed.org/cookbook/SPI-driven-QVGA-TFT code for the older LCD board.

The lib is using the 4 line serial data interface. The IM pins have to be set to 1110 (IM3-IM0) to use this mode. It use the SPI hardware.

I have started to speed up the lib with using DMA and direct SPI programming. To do this I have to split the code for the different platforms. To prevent unreadable code with a lot of #ifdef... I have create a new file. The #ifdef definition around is switching between the platforms. I will add the other Nucleo platforms. If you want to support others - see ..._NUCLEO.cpp , port and send me the code to add.

Display 1

If you use the TFT Proto from MikroElektronika http://www.mikroe.com/eng/products/view/474/tft-proto-board/ you have to connect : /media/uploads/dreschpe/tft_proto.png

MBEDDisplay
+ 3,3V3,3V
GNDGND
mosiSDI
misoSDO
sckRS
csCS
resetRST
dcWR/SCL
GNDIM0
+3,3VIM1 IM2 IM3
GNDDB0 - DB17
GNDRD

The backlite LED need a resistor to limit the current. You can use two 10R resistors parallel to get 5R driven by 3.3V.

Display 2

Watterott is also selling a ILI9341 based QVGA TFT : http://www.watterott.com/de/MI0283QT-2-Adapter

Unfortunately this adapter is set to 9 bit SPI mode via the mode pins IM0-IM3. If you want to patch this - like I have done - you have to desolder the TFT from the pcb to cut some traces. This is a flexible print. Only for people with soldering skills ! You also have to get access to pin 36 for the dc signal. Cut the GND connection. You can use the level converter used for the LCD_LED signal. Mosfet Q1 can be driven with a logic signal without converter. Watterott will change this in a future revision.

/media/uploads/dreschpe/mi0283qt_v12_patch.pdf

Display 3

There are inexpensive displays from china. You can get them at: http://www.banggood.com/2_2-Inch-Serial-TFT-SPI-LCD-Screen-Module-HD-240-X-320-5110-Compatible-p-912854.html The board has also a SD card connector at the backside, but no touch.

/media/uploads/dreschpe/tft3_1.jpg /media/uploads/dreschpe/tft3_2.jpg

The board can be used without modification. Connect VCC with 5V USB out. There is a voltage regulator on board. To use the SD card simply import the SDFileSystem and connect it to the second SPI.

Fonts

How to get nice looking fonts ?

To print characters to a graphic screen we need a font. To code a font by paper is ok for a small lcd, but for a 320*240 pixel display we need bigger fonts. A 12*12 pixel font is readable, but a lot of work to construct.

Fonts can be made with the GLCD Font Creator also from http://www.mikroe.com .

With this program you can load a window font and convert it into a c-array. To use this Font with my lib you have to add 4 parameter at the beginning of the font array. - the number of byte / char - the vertial size in pixel - the horizontal size in pixel - the number of byte per vertical line (it is vertical size / 8 ) You also have to change the array to char[]. After that you can switch between different fonts with set_font(unsigned char* font); The horizontal size of each character is also stored in the font. It look better if you use bigger fonts or italic. The letter M is wider than a l.

Here are some Fonts from me : http://mbed.org/users/dreschpe/code/TFT_fonts/

The small made for the mbed lab board : http://mbed.org/users/dreschpe/code/LCD_fonts/

And from Peter Holzleitner : http://mbed.org/users/pholzleitner/code/SourceCodePro31-SB/

Text commands :

You can use the claim() function to redirect the output to stdout or stderr to the TFT. After claim(stdout) you can simply use the printf function to print to the TFT.

  • locate(x,y); function is used to setup the cursor position. x,y are the pixel position. This was changed from row,column in older lib !

There are two parameter to setup the color of the text :

  • background(color);
  • foreground(color); All color are 16bit: R5 G6 B5.
  • set_orientation(); This command select one of the 4 directions to use the display. This command is also working on the graphical commands.

Graphics

Graphic commands :

  • cls(); Fill the screen with background color
  • pixel(x,y,color); set a single pixel at x,y with color
  • line(x0,y0,x1,y1,color); draw a line from x0,y0 to x1,y1 with color
  • rect(x0,y0,x1,y1,color); draw a rectangle x0,y0 to x1,y1 with color
  • fillrect(x0,y0,x1,y1,color); draw a filled rectangle
  • circle( x0,y0,radius ,color); draw a circle around x0,y0 with radius
  • fillcircle(x0,y0,radius ,color); draw a filled circle around x0,y0 with radius
  • Bitmap(x0,y0,w,h,*bitmap); paint a bitmap with width w and high h starting at x0,y0 (upper left corner)
  • BMP_16(x0,y0,*bmp); paint a bmp file out of the internal drive or a SD-card

How to transfer a grafic to the mbed ?

The hard way - but fast to load :

Load from mbed flash. It consume a lot of flash memory. To construct a bitmap array we can use gimp. http://www.gimp.org/ Load a image (edit and resize) and export it as BMP. You have to select the option 16 bit R5 G6 B5 !

To convert this file into a c-array you can use the hex-editor winhex. (http://www.x-ways.net/winhex/index-m.html) The eval version can handle the small files. We don`t need the bmp header. Mark the data starting at offset 0x46 to the end of file. Use "edit -> copy block -> C Source" to export this data as C array. Paste the data into a C file into the mbed compiler. The editor will generate a array of char[]. To use 16 bit DMA on this we have to put a __align(2) in front of the definition. To put it into Flash we change it to static const unsigned char bmp[]{...}

__align(2)
static const unsigned char bmp[]{
      0xCB, 0x5A, 0x5C, 0xE7,....

};

The easy way - but slower to load:

With the BMP_16 command we can load a picture out of the internal drive or a SD-card to the display.

  • BMP_16(x0,y0,"/local/test.bmp"); paint test.bmp out of the internal drive to x0, y0
  • BMP_16(x0,y0,"/sd/test.bmp"); paint test.bmp out of a external SD-card to x0, y0

simply copy test.bmp to the mbed usb drive or the SD-card. The bmp has to be saved with the options 16 bit R5 G6 B5 ! You can use the program gimp to convert pictures into the 16 bit bmp format.

sample code

http://mbed.org/users/dreschpe/code/TFT_Test_ILI9341/

// example to test the TFT Display
// Thanks to the GraphicsDisplay and TextDisplay classes
// test2.bmp has to be on the mbed file system

#include "stdio.h"
#include "mbed.h"
#include "SPI_TFT_ILI9341.h"
#include "string"
#include "Arial12x12.h"
#include "Arial24x23.h"
#include "Arial28x28.h"
#include "font_big.h"

extern unsigned char p1[];  // the mbed logo

DigitalOut LCD_LED(p21); // the Watterott display has a backlight switch
DigitalOut CS_Touch(p15); // disable the touch controller on the Watterott display

// the TFT is connected to SPI pin 5-7
SPI_TFT_ILI9341 TFT(p5, p6, p7, p8, p9, p10,"TFT"); // mosi, miso, sclk, cs, reset, dc

int main()
{
    int i;
    LCD_LED = 1;  // backlight on
    CS_Touch = 1; 
   
    TFT.claim(stdout);      // send stdout to the TFT display
    //TFT.claim(stderr);      // send stderr to the TFT display
    TFT.set_orientation(1);
    TFT.background(Black);    // set background to black
    TFT.foreground(White);    // set chars to white
    TFT.cls();                // clear the screen

    //first show the 4 directions
    TFT.set_orientation(0);
    TFT.background(Black);
    TFT.cls();

    TFT.set_font((unsigned char*) Arial12x12);
    TFT.locate(0,0);
    printf("  Hello Mbed 0");

    TFT.set_orientation(1);
    TFT.locate(0,0);
    printf("  Hello Mbed 1");
    TFT.set_orientation(2);
    TFT.locate(0,0);
    printf("  Hello Mbed 2");
    TFT.set_orientation(3);
    TFT.locate(0,0);
    printf("  Hello Mbed 3");
    TFT.set_orientation(1);
    TFT.set_font((unsigned char*) Arial24x23);
    TFT.locate(50,100);
    TFT.printf("TFT orientation");

/media/uploads/dreschpe/orient.jpg

// draw some graphics
    TFT.cls();
    TFT.set_font((unsigned char*) Arial24x23);
    TFT.locate(100,100);
    TFT.printf("Graphic");

    TFT.line(0,0,100,0,Green);
    TFT.line(0,0,0,200,Green);
    TFT.line(0,0,100,200,Green);

    TFT.rect(100,50,150,100,Red);
    TFT.fillrect(180,25,220,70,Blue);

    TFT.circle(80,150,33,White);
    TFT.fillcircle(160,190,20,Yellow);

    double s;

    for (i=0; i<320; i++) {
        s =20 * sin((long double) i / 10 );
        TFT.pixel(i,100 + (int)s ,Red);
    }

/media/uploads/dreschpe/grafik.jpg

   // bigger text
    TFT.foreground(White);
    TFT.background(Blue);
    TFT.cls();
    TFT.set_font((unsigned char*) Arial24x23);
    TFT.locate(0,0);
    TFT.printf("Different Fonts :");

    TFT.set_font((unsigned char*) Neu42x35);
    TFT.locate(0,30);
    TFT.printf("Hello Mbed 1");
    TFT.set_font((unsigned char*) Arial24x23);
    TFT.locate(20,80);
    TFT.printf("Hello Mbed 2");
    TFT.set_font((unsigned char*) Arial12x12);
    TFT.locate(35,120);
    TFT.printf("Hello Mbed 3");

/media/uploads/dreschpe/fonts2.jpg

    // mbed logo from flash
    // defined in graphics.c
    //__align(4)
    //unsigned char p1[18920] = {
    //0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, ....
    // 
    TFT.background(Black);
    TFT.cls();

    TFT.locate(10,10);
    TFT.printf("Graphic from Flash");

    TFT.Bitmap(90,90,172,55,p1);

/media/uploads/dreschpe/mbed.jpg

  
  #include "SDFileSystem.h"
  // connect a sd-card to the second spi or use the local filesystem of the LPC   
  SDFileSystem sd(p11, p12, p13, p14, "sd"); // mosi,miso,sck,cs
  TFT.cls();
  TFT.locate(10,110);
  TFT.printf("Graphic from external SD-card");
  int err = TFT.BMP_16(1,140,"/sd/test.bmp");  // load test.bmp from external SD-card
  TFT.locate(10,120);
  if (err != 1) TFT.printf(" - Err: %d",err);

/media/uploads/dreschpe/bmp16.jpg

Committer:
dreschpe
Date:
Sun Jun 22 22:32:01 2014 +0000
Revision:
10:50f88bd5557f
Parent:
9:423e6a952472
Child:
11:59eca2723ec5
fix warning

Who changed what in which revision?

UserRevisionLine numberNew contents of line
dreschpe 0:da1bf437cbc1 1 /* mbed library for 240*320 pixel display TFT based on ILI9341 LCD Controller
dreschpe 0:da1bf437cbc1 2 * Copyright (c) 2013 Peter Drescher - DC2PD
dreschpe 0:da1bf437cbc1 3 *
dreschpe 0:da1bf437cbc1 4 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
dreschpe 0:da1bf437cbc1 5 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
dreschpe 0:da1bf437cbc1 6 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
dreschpe 0:da1bf437cbc1 7 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
dreschpe 0:da1bf437cbc1 8 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
dreschpe 0:da1bf437cbc1 9 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
dreschpe 0:da1bf437cbc1 10 * THE SOFTWARE.
dreschpe 0:da1bf437cbc1 11 */
dreschpe 0:da1bf437cbc1 12
dreschpe 0:da1bf437cbc1 13 // 12.06.13 fork from SPI_TFT code because controller is different ...
dreschpe 2:0a16083193a4 14 // 14.07.13 Test with real display and bugfix
dreschpe 4:f018e272220b 15 // 18.10.13 Better Circle function from Michael Ammann
dreschpe 5:55aed13f2630 16 // 22.10.13 Fixes for Kinetis Board - 8 bit spi
dreschpe 6:fe07ae8329f7 17 // 26.01.14 Change interface for BMP_16 to also use SD-cards
dreschpe 9:423e6a952472 18 // 23.06.14 switch back to old Version - fork for L152
dreschpe 0:da1bf437cbc1 19
dreschpe 0:da1bf437cbc1 20 #include "SPI_TFT_ILI9341.h"
dreschpe 0:da1bf437cbc1 21 #include "mbed.h"
dreschpe 0:da1bf437cbc1 22
dreschpe 0:da1bf437cbc1 23 #define BPP 16 // Bits per pixel
dreschpe 6:fe07ae8329f7 24
dreschpe 0:da1bf437cbc1 25 //extern Serial pc;
dreschpe 0:da1bf437cbc1 26 //extern DigitalOut xx; // debug !!
dreschpe 0:da1bf437cbc1 27
dreschpe 0:da1bf437cbc1 28 SPI_TFT_ILI9341::SPI_TFT_ILI9341(PinName mosi, PinName miso, PinName sclk, PinName cs, PinName reset, PinName dc, const char *name)
dreschpe 10:50f88bd5557f 29 : GraphicsDisplay(name), _spi(mosi, miso, sclk), _cs(cs), _reset(reset), _dc(dc)
dreschpe 0:da1bf437cbc1 30 {
dreschpe 6:fe07ae8329f7 31 clk = sclk;
dreschpe 0:da1bf437cbc1 32 orientation = 0;
dreschpe 0:da1bf437cbc1 33 char_x = 0;
dreschpe 0:da1bf437cbc1 34 tft_reset();
dreschpe 0:da1bf437cbc1 35 }
dreschpe 0:da1bf437cbc1 36
dreschpe 0:da1bf437cbc1 37 int SPI_TFT_ILI9341::width()
dreschpe 0:da1bf437cbc1 38 {
dreschpe 0:da1bf437cbc1 39 if (orientation == 0 || orientation == 2) return 240;
dreschpe 0:da1bf437cbc1 40 else return 320;
dreschpe 0:da1bf437cbc1 41 }
dreschpe 0:da1bf437cbc1 42
dreschpe 0:da1bf437cbc1 43
dreschpe 0:da1bf437cbc1 44 int SPI_TFT_ILI9341::height()
dreschpe 0:da1bf437cbc1 45 {
dreschpe 0:da1bf437cbc1 46 if (orientation == 0 || orientation == 2) return 320;
dreschpe 0:da1bf437cbc1 47 else return 240;
dreschpe 0:da1bf437cbc1 48 }
dreschpe 0:da1bf437cbc1 49
dreschpe 0:da1bf437cbc1 50
dreschpe 2:0a16083193a4 51 void SPI_TFT_ILI9341::set_orientation(unsigned int o)
dreschpe 0:da1bf437cbc1 52 {
dreschpe 0:da1bf437cbc1 53 orientation = o;
dreschpe 2:0a16083193a4 54 wr_cmd(0x36); // MEMORY_ACCESS_CONTROL
dreschpe 0:da1bf437cbc1 55 switch (orientation) {
dreschpe 0:da1bf437cbc1 56 case 0:
dreschpe 2:0a16083193a4 57 _spi.write(0x48);
dreschpe 0:da1bf437cbc1 58 break;
dreschpe 0:da1bf437cbc1 59 case 1:
dreschpe 2:0a16083193a4 60 _spi.write(0x28);
dreschpe 0:da1bf437cbc1 61 break;
dreschpe 0:da1bf437cbc1 62 case 2:
dreschpe 2:0a16083193a4 63 _spi.write(0x88);
dreschpe 0:da1bf437cbc1 64 break;
dreschpe 0:da1bf437cbc1 65 case 3:
dreschpe 2:0a16083193a4 66 _spi.write(0xE8);
dreschpe 0:da1bf437cbc1 67 break;
dreschpe 0:da1bf437cbc1 68 }
dreschpe 2:0a16083193a4 69 _cs = 1;
dreschpe 0:da1bf437cbc1 70 WindowMax();
dreschpe 2:0a16083193a4 71 }
dreschpe 0:da1bf437cbc1 72
dreschpe 0:da1bf437cbc1 73
dreschpe 0:da1bf437cbc1 74 // write command to tft register
dreschpe 0:da1bf437cbc1 75
dreschpe 0:da1bf437cbc1 76 void SPI_TFT_ILI9341::wr_cmd(unsigned char cmd)
dreschpe 0:da1bf437cbc1 77 {
dreschpe 0:da1bf437cbc1 78 _dc = 0;
dreschpe 0:da1bf437cbc1 79 _cs = 0;
dreschpe 0:da1bf437cbc1 80 _spi.write(cmd); // mbed lib
dreschpe 0:da1bf437cbc1 81 _dc = 1;
dreschpe 0:da1bf437cbc1 82 }
dreschpe 0:da1bf437cbc1 83
dreschpe 0:da1bf437cbc1 84
dreschpe 0:da1bf437cbc1 85
dreschpe 0:da1bf437cbc1 86 void SPI_TFT_ILI9341::wr_dat(unsigned char dat)
dreschpe 0:da1bf437cbc1 87 {
dreschpe 0:da1bf437cbc1 88 _spi.write(dat); // mbed lib
dreschpe 0:da1bf437cbc1 89 }
dreschpe 0:da1bf437cbc1 90
dreschpe 0:da1bf437cbc1 91
dreschpe 0:da1bf437cbc1 92
dreschpe 6:fe07ae8329f7 93 // the ILI9341 can read
dreschpe 6:fe07ae8329f7 94
dreschpe 6:fe07ae8329f7 95 char SPI_TFT_ILI9341::rd_byte(unsigned char cmd)
dreschpe 6:fe07ae8329f7 96 {
dreschpe 6:fe07ae8329f7 97 char r;
dreschpe 6:fe07ae8329f7 98 _dc = 0;
dreschpe 6:fe07ae8329f7 99 _cs = 0;
dreschpe 6:fe07ae8329f7 100 _spi.write(cmd); // mbed lib
dreschpe 6:fe07ae8329f7 101 _cs = 1;
dreschpe 6:fe07ae8329f7 102 r = _spi.write(0xff);
dreschpe 6:fe07ae8329f7 103 _cs = 1;
dreschpe 6:fe07ae8329f7 104 return(r);
dreschpe 6:fe07ae8329f7 105 }
dreschpe 0:da1bf437cbc1 106
dreschpe 6:fe07ae8329f7 107 // read 32 bit
dreschpe 6:fe07ae8329f7 108 int SPI_TFT_ILI9341::rd_32(unsigned char cmd)
dreschpe 6:fe07ae8329f7 109 {
dreschpe 6:fe07ae8329f7 110 int d;
dreschpe 6:fe07ae8329f7 111 char r;
dreschpe 6:fe07ae8329f7 112 _dc = 0;
dreschpe 6:fe07ae8329f7 113 _cs = 0;
dreschpe 6:fe07ae8329f7 114 d = cmd;
dreschpe 6:fe07ae8329f7 115 d = d << 1;
dreschpe 6:fe07ae8329f7 116 _spi.format(9,3); // we have to add a dummy clock cycle
dreschpe 6:fe07ae8329f7 117 _spi.write(d);
dreschpe 6:fe07ae8329f7 118 _spi.format(8,3);
dreschpe 6:fe07ae8329f7 119 _dc = 1;
dreschpe 6:fe07ae8329f7 120 r = _spi.write(0xff);
dreschpe 6:fe07ae8329f7 121 d = r;
dreschpe 6:fe07ae8329f7 122 r = _spi.write(0xff);
dreschpe 6:fe07ae8329f7 123 d = (d << 8) | r;
dreschpe 6:fe07ae8329f7 124 r = _spi.write(0xff);
dreschpe 6:fe07ae8329f7 125 d = (d << 8) | r;
dreschpe 6:fe07ae8329f7 126 r = _spi.write(0xff);
dreschpe 6:fe07ae8329f7 127 d = (d << 8) | r;
dreschpe 6:fe07ae8329f7 128 _cs = 1;
dreschpe 6:fe07ae8329f7 129 return(d);
dreschpe 6:fe07ae8329f7 130 }
dreschpe 0:da1bf437cbc1 131
dreschpe 6:fe07ae8329f7 132 int SPI_TFT_ILI9341::Read_ID(void){
dreschpe 6:fe07ae8329f7 133 int r;
dreschpe 6:fe07ae8329f7 134 r = rd_byte(0x0A);
dreschpe 6:fe07ae8329f7 135 r = rd_byte(0x0A);
dreschpe 6:fe07ae8329f7 136 r = rd_byte(0x0A);
dreschpe 6:fe07ae8329f7 137 r = rd_byte(0x0A);
dreschpe 6:fe07ae8329f7 138 return(r);
dreschpe 6:fe07ae8329f7 139 }
dreschpe 0:da1bf437cbc1 140
dreschpe 0:da1bf437cbc1 141
dreschpe 1:6d6125e88de7 142 // Init code based on MI0283QT datasheet
dreschpe 1:6d6125e88de7 143
dreschpe 0:da1bf437cbc1 144 void SPI_TFT_ILI9341::tft_reset()
dreschpe 0:da1bf437cbc1 145 {
dreschpe 2:0a16083193a4 146 _spi.format(8,3); // 8 bit spi mode 3
dreschpe 7:4c30bea883bc 147 _spi.frequency(10000000); // 10 Mhz SPI clock
dreschpe 0:da1bf437cbc1 148 _cs = 1; // cs high
dreschpe 0:da1bf437cbc1 149 _dc = 1; // dc high
dreschpe 0:da1bf437cbc1 150 _reset = 0; // display reset
dreschpe 0:da1bf437cbc1 151
dreschpe 0:da1bf437cbc1 152 wait_us(50);
dreschpe 1:6d6125e88de7 153 _reset = 1; // end hardware reset
dreschpe 0:da1bf437cbc1 154 wait_ms(5);
dreschpe 1:6d6125e88de7 155
dreschpe 1:6d6125e88de7 156 wr_cmd(0x01); // SW reset
dreschpe 1:6d6125e88de7 157 wait_ms(5);
dreschpe 1:6d6125e88de7 158 wr_cmd(0x28); // display off
dreschpe 0:da1bf437cbc1 159
dreschpe 0:da1bf437cbc1 160 /* Start Initial Sequence ----------------------------------------------------*/
dreschpe 1:6d6125e88de7 161 wr_cmd(0xCF);
dreschpe 1:6d6125e88de7 162 _spi.write(0x00);
dreschpe 1:6d6125e88de7 163 _spi.write(0x83);
dreschpe 1:6d6125e88de7 164 _spi.write(0x30);
dreschpe 1:6d6125e88de7 165 _cs = 1;
dreschpe 1:6d6125e88de7 166
dreschpe 1:6d6125e88de7 167 wr_cmd(0xED);
dreschpe 1:6d6125e88de7 168 _spi.write(0x64);
dreschpe 1:6d6125e88de7 169 _spi.write(0x03);
dreschpe 1:6d6125e88de7 170 _spi.write(0x12);
dreschpe 1:6d6125e88de7 171 _spi.write(0x81);
dreschpe 1:6d6125e88de7 172 _cs = 1;
dreschpe 1:6d6125e88de7 173
dreschpe 1:6d6125e88de7 174 wr_cmd(0xE8);
dreschpe 1:6d6125e88de7 175 _spi.write(0x85);
dreschpe 1:6d6125e88de7 176 _spi.write(0x01);
dreschpe 1:6d6125e88de7 177 _spi.write(0x79);
dreschpe 1:6d6125e88de7 178 _cs = 1;
dreschpe 1:6d6125e88de7 179
dreschpe 1:6d6125e88de7 180 wr_cmd(0xCB);
dreschpe 0:da1bf437cbc1 181 _spi.write(0x39);
dreschpe 0:da1bf437cbc1 182 _spi.write(0x2C);
dreschpe 0:da1bf437cbc1 183 _spi.write(0x00);
dreschpe 0:da1bf437cbc1 184 _spi.write(0x34);
dreschpe 0:da1bf437cbc1 185 _spi.write(0x02);
dreschpe 0:da1bf437cbc1 186 _cs = 1;
dreschpe 1:6d6125e88de7 187
dreschpe 1:6d6125e88de7 188 wr_cmd(0xF7);
dreschpe 1:6d6125e88de7 189 _spi.write(0x20);
dreschpe 0:da1bf437cbc1 190 _cs = 1;
dreschpe 1:6d6125e88de7 191
dreschpe 1:6d6125e88de7 192 wr_cmd(0xEA);
dreschpe 1:6d6125e88de7 193 _spi.write(0x00);
dreschpe 1:6d6125e88de7 194 _spi.write(0x00);
dreschpe 0:da1bf437cbc1 195 _cs = 1;
dreschpe 1:6d6125e88de7 196
dreschpe 0:da1bf437cbc1 197 wr_cmd(0xC0); // POWER_CONTROL_1
dreschpe 1:6d6125e88de7 198 _spi.write(0x26);
dreschpe 0:da1bf437cbc1 199 _cs = 1;
dreschpe 1:6d6125e88de7 200
dreschpe 0:da1bf437cbc1 201 wr_cmd(0xC1); // POWER_CONTROL_2
dreschpe 0:da1bf437cbc1 202 _spi.write(0x11);
dreschpe 0:da1bf437cbc1 203 _cs = 1;
dreschpe 1:6d6125e88de7 204
dreschpe 0:da1bf437cbc1 205 wr_cmd(0xC5); // VCOM_CONTROL_1
dreschpe 1:6d6125e88de7 206 _spi.write(0x35);
dreschpe 1:6d6125e88de7 207 _spi.write(0x3E);
dreschpe 0:da1bf437cbc1 208 _cs = 1;
dreschpe 1:6d6125e88de7 209
dreschpe 0:da1bf437cbc1 210 wr_cmd(0xC7); // VCOM_CONTROL_2
dreschpe 1:6d6125e88de7 211 _spi.write(0xBE);
dreschpe 0:da1bf437cbc1 212 _cs = 1;
dreschpe 1:6d6125e88de7 213
dreschpe 0:da1bf437cbc1 214 wr_cmd(0x36); // MEMORY_ACCESS_CONTROL
dreschpe 0:da1bf437cbc1 215 _spi.write(0x48);
dreschpe 0:da1bf437cbc1 216 _cs = 1;
dreschpe 1:6d6125e88de7 217
dreschpe 1:6d6125e88de7 218 wr_cmd(0x3A); // COLMOD_PIXEL_FORMAT_SET
dreschpe 1:6d6125e88de7 219 _spi.write(0x55); // 16 bit pixel
dreschpe 1:6d6125e88de7 220 _cs = 1;
dreschpe 1:6d6125e88de7 221
dreschpe 1:6d6125e88de7 222 wr_cmd(0xB1); // Frame Rate
dreschpe 1:6d6125e88de7 223 _spi.write(0x00);
dreschpe 1:6d6125e88de7 224 _spi.write(0x1B);
dreschpe 1:6d6125e88de7 225 _cs = 1;
dreschpe 1:6d6125e88de7 226
dreschpe 1:6d6125e88de7 227 wr_cmd(0xF2); // Gamma Function Disable
dreschpe 1:6d6125e88de7 228 _spi.write(0x08);
dreschpe 1:6d6125e88de7 229 _cs = 1;
dreschpe 1:6d6125e88de7 230
dreschpe 1:6d6125e88de7 231 wr_cmd(0x26);
dreschpe 1:6d6125e88de7 232 _spi.write(0x01); // gamma set for curve 01/2/04/08
dreschpe 1:6d6125e88de7 233 _cs = 1;
dreschpe 1:6d6125e88de7 234
dreschpe 1:6d6125e88de7 235 wr_cmd(0xE0); // positive gamma correction
dreschpe 1:6d6125e88de7 236 _spi.write(0x1F);
dreschpe 1:6d6125e88de7 237 _spi.write(0x1A);
dreschpe 1:6d6125e88de7 238 _spi.write(0x18);
dreschpe 1:6d6125e88de7 239 _spi.write(0x0A);
dreschpe 1:6d6125e88de7 240 _spi.write(0x0F);
dreschpe 1:6d6125e88de7 241 _spi.write(0x06);
dreschpe 1:6d6125e88de7 242 _spi.write(0x45);
dreschpe 1:6d6125e88de7 243 _spi.write(0x87);
dreschpe 1:6d6125e88de7 244 _spi.write(0x32);
dreschpe 1:6d6125e88de7 245 _spi.write(0x0A);
dreschpe 1:6d6125e88de7 246 _spi.write(0x07);
dreschpe 1:6d6125e88de7 247 _spi.write(0x02);
dreschpe 1:6d6125e88de7 248 _spi.write(0x07);
dreschpe 1:6d6125e88de7 249 _spi.write(0x05);
dreschpe 1:6d6125e88de7 250 _spi.write(0x00);
dreschpe 1:6d6125e88de7 251 _cs = 1;
dreschpe 1:6d6125e88de7 252
dreschpe 1:6d6125e88de7 253 wr_cmd(0xE1); // negativ gamma correction
dreschpe 1:6d6125e88de7 254 _spi.write(0x00);
dreschpe 1:6d6125e88de7 255 _spi.write(0x25);
dreschpe 1:6d6125e88de7 256 _spi.write(0x27);
dreschpe 1:6d6125e88de7 257 _spi.write(0x05);
dreschpe 1:6d6125e88de7 258 _spi.write(0x10);
dreschpe 1:6d6125e88de7 259 _spi.write(0x09);
dreschpe 1:6d6125e88de7 260 _spi.write(0x3A);
dreschpe 1:6d6125e88de7 261 _spi.write(0x78);
dreschpe 1:6d6125e88de7 262 _spi.write(0x4D);
dreschpe 1:6d6125e88de7 263 _spi.write(0x05);
dreschpe 1:6d6125e88de7 264 _spi.write(0x18);
dreschpe 1:6d6125e88de7 265 _spi.write(0x0D);
dreschpe 1:6d6125e88de7 266 _spi.write(0x38);
dreschpe 1:6d6125e88de7 267 _spi.write(0x3A);
dreschpe 1:6d6125e88de7 268 _spi.write(0x1F);
dreschpe 1:6d6125e88de7 269 _cs = 1;
dreschpe 1:6d6125e88de7 270
dreschpe 1:6d6125e88de7 271 WindowMax ();
dreschpe 1:6d6125e88de7 272
dreschpe 1:6d6125e88de7 273 //wr_cmd(0x34); // tearing effect off
dreschpe 1:6d6125e88de7 274 //_cs = 1;
dreschpe 1:6d6125e88de7 275
dreschpe 1:6d6125e88de7 276 //wr_cmd(0x35); // tearing effect on
dreschpe 1:6d6125e88de7 277 //_cs = 1;
dreschpe 1:6d6125e88de7 278
dreschpe 1:6d6125e88de7 279 wr_cmd(0xB7); // entry mode
dreschpe 1:6d6125e88de7 280 _spi.write(0x07);
dreschpe 1:6d6125e88de7 281 _cs = 1;
dreschpe 1:6d6125e88de7 282
dreschpe 1:6d6125e88de7 283 wr_cmd(0xB6); // display function control
dreschpe 1:6d6125e88de7 284 _spi.write(0x0A);
dreschpe 1:6d6125e88de7 285 _spi.write(0x82);
dreschpe 1:6d6125e88de7 286 _spi.write(0x27);
dreschpe 1:6d6125e88de7 287 _spi.write(0x00);
dreschpe 1:6d6125e88de7 288 _cs = 1;
dreschpe 1:6d6125e88de7 289
dreschpe 1:6d6125e88de7 290 wr_cmd(0x11); // sleep out
dreschpe 1:6d6125e88de7 291 _cs = 1;
dreschpe 1:6d6125e88de7 292
dreschpe 1:6d6125e88de7 293 wait_ms(100);
dreschpe 1:6d6125e88de7 294
dreschpe 1:6d6125e88de7 295 wr_cmd(0x29); // display on
dreschpe 1:6d6125e88de7 296 _cs = 1;
dreschpe 1:6d6125e88de7 297
dreschpe 1:6d6125e88de7 298 wait_ms(100);
dreschpe 1:6d6125e88de7 299
dreschpe 1:6d6125e88de7 300 }
dreschpe 0:da1bf437cbc1 301
dreschpe 0:da1bf437cbc1 302
dreschpe 0:da1bf437cbc1 303 void SPI_TFT_ILI9341::pixel(int x, int y, int color)
dreschpe 0:da1bf437cbc1 304 {
dreschpe 0:da1bf437cbc1 305 wr_cmd(0x2A);
dreschpe 0:da1bf437cbc1 306 _spi.write(x >> 8);
dreschpe 0:da1bf437cbc1 307 _spi.write(x);
dreschpe 0:da1bf437cbc1 308 _cs = 1;
dreschpe 0:da1bf437cbc1 309 wr_cmd(0x2B);
dreschpe 0:da1bf437cbc1 310 _spi.write(y >> 8);
dreschpe 0:da1bf437cbc1 311 _spi.write(y);
dreschpe 0:da1bf437cbc1 312 _cs = 1;
dreschpe 5:55aed13f2630 313 wr_cmd(0x2C); // send pixel
dreschpe 5:55aed13f2630 314 #if defined TARGET_KL25Z // 8 Bit SPI
dreschpe 5:55aed13f2630 315 _spi.write(color >> 8);
dreschpe 5:55aed13f2630 316 _spi.write(color & 0xff);
dreschpe 5:55aed13f2630 317 #else
dreschpe 0:da1bf437cbc1 318 _spi.format(16,3); // switch to 16 bit Mode 3
dreschpe 0:da1bf437cbc1 319 _spi.write(color); // Write D0..D15
dreschpe 0:da1bf437cbc1 320 _spi.format(8,3);
dreschpe 5:55aed13f2630 321 #endif
dreschpe 0:da1bf437cbc1 322 _cs = 1;
dreschpe 0:da1bf437cbc1 323 }
dreschpe 0:da1bf437cbc1 324
dreschpe 0:da1bf437cbc1 325
dreschpe 0:da1bf437cbc1 326 void SPI_TFT_ILI9341::window (unsigned int x, unsigned int y, unsigned int w, unsigned int h)
dreschpe 0:da1bf437cbc1 327 {
dreschpe 0:da1bf437cbc1 328 wr_cmd(0x2A);
dreschpe 0:da1bf437cbc1 329 _spi.write(x >> 8);
dreschpe 0:da1bf437cbc1 330 _spi.write(x);
dreschpe 0:da1bf437cbc1 331 _spi.write((x+w-1) >> 8);
dreschpe 0:da1bf437cbc1 332 _spi.write(x+w-1);
dreschpe 0:da1bf437cbc1 333
dreschpe 0:da1bf437cbc1 334 _cs = 1;
dreschpe 0:da1bf437cbc1 335 wr_cmd(0x2B);
dreschpe 0:da1bf437cbc1 336 _spi.write(y >> 8);
dreschpe 0:da1bf437cbc1 337 _spi.write(y);
dreschpe 0:da1bf437cbc1 338 _spi.write((y+h-1) >> 8);
dreschpe 0:da1bf437cbc1 339 _spi.write(y+h-1);
dreschpe 0:da1bf437cbc1 340 _cs = 1;
dreschpe 0:da1bf437cbc1 341 }
dreschpe 0:da1bf437cbc1 342
dreschpe 0:da1bf437cbc1 343
dreschpe 0:da1bf437cbc1 344 void SPI_TFT_ILI9341::WindowMax (void)
dreschpe 0:da1bf437cbc1 345 {
dreschpe 0:da1bf437cbc1 346 window (0, 0, width(), height());
dreschpe 0:da1bf437cbc1 347 }
dreschpe 0:da1bf437cbc1 348
dreschpe 0:da1bf437cbc1 349
dreschpe 0:da1bf437cbc1 350
dreschpe 0:da1bf437cbc1 351 void SPI_TFT_ILI9341::cls (void)
dreschpe 0:da1bf437cbc1 352 {
dreschpe 0:da1bf437cbc1 353 int pixel = ( width() * height());
dreschpe 0:da1bf437cbc1 354 WindowMax();
dreschpe 5:55aed13f2630 355 wr_cmd(0x2C); // send pixel
dreschpe 5:55aed13f2630 356 #if defined TARGET_KL25Z // 8 Bit SPI
dreschpe 5:55aed13f2630 357 unsigned int i;
dreschpe 5:55aed13f2630 358 for (i = 0; i < ( width() * height()); i++){
dreschpe 5:55aed13f2630 359 _spi.write(_background >> 8);
dreschpe 5:55aed13f2630 360 _spi.write(_background & 0xff);
dreschpe 5:55aed13f2630 361 }
dreschpe 5:55aed13f2630 362
dreschpe 5:55aed13f2630 363 #else
dreschpe 0:da1bf437cbc1 364 _spi.format(16,3); // switch to 16 bit Mode 3
dreschpe 0:da1bf437cbc1 365 unsigned int i;
dreschpe 0:da1bf437cbc1 366 for (i = 0; i < ( width() * height()); i++)
dreschpe 5:55aed13f2630 367 _spi.write(_background);
dreschpe 5:55aed13f2630 368 _spi.format(8,3);
dreschpe 5:55aed13f2630 369 #endif
dreschpe 5:55aed13f2630 370 _cs = 1;
dreschpe 0:da1bf437cbc1 371 }
dreschpe 0:da1bf437cbc1 372
dreschpe 0:da1bf437cbc1 373
dreschpe 0:da1bf437cbc1 374 void SPI_TFT_ILI9341::circle(int x0, int y0, int r, int color)
dreschpe 0:da1bf437cbc1 375 {
dreschpe 0:da1bf437cbc1 376
mazgch 3:3d7298360e45 377 int x = -r, y = 0, err = 2-2*r, e2;
mazgch 3:3d7298360e45 378 do {
mazgch 3:3d7298360e45 379 pixel(x0-x, y0+y,color);
mazgch 3:3d7298360e45 380 pixel(x0+x, y0+y,color);
mazgch 3:3d7298360e45 381 pixel(x0+x, y0-y,color);
mazgch 3:3d7298360e45 382 pixel(x0-x, y0-y,color);
mazgch 3:3d7298360e45 383 e2 = err;
mazgch 3:3d7298360e45 384 if (e2 <= y) {
mazgch 3:3d7298360e45 385 err += ++y*2+1;
mazgch 3:3d7298360e45 386 if (-x == y && e2 <= x) e2 = 0;
mazgch 3:3d7298360e45 387 }
mazgch 3:3d7298360e45 388 if (e2 > x) err += ++x*2+1;
mazgch 3:3d7298360e45 389 } while (x <= 0);
dreschpe 4:f018e272220b 390
dreschpe 0:da1bf437cbc1 391 }
dreschpe 0:da1bf437cbc1 392
mazgch 3:3d7298360e45 393 void SPI_TFT_ILI9341::fillcircle(int x0, int y0, int r, int color)
dreschpe 0:da1bf437cbc1 394 {
mazgch 3:3d7298360e45 395 int x = -r, y = 0, err = 2-2*r, e2;
mazgch 3:3d7298360e45 396 do {
mazgch 3:3d7298360e45 397 vline(x0-x, y0-y, y0+y, color);
mazgch 3:3d7298360e45 398 vline(x0+x, y0-y, y0+y, color);
mazgch 3:3d7298360e45 399 e2 = err;
mazgch 3:3d7298360e45 400 if (e2 <= y) {
mazgch 3:3d7298360e45 401 err += ++y*2+1;
mazgch 3:3d7298360e45 402 if (-x == y && e2 <= x) e2 = 0;
mazgch 3:3d7298360e45 403 }
mazgch 3:3d7298360e45 404 if (e2 > x) err += ++x*2+1;
mazgch 3:3d7298360e45 405 } while (x <= 0);
dreschpe 0:da1bf437cbc1 406 }
dreschpe 0:da1bf437cbc1 407
dreschpe 0:da1bf437cbc1 408
dreschpe 0:da1bf437cbc1 409 void SPI_TFT_ILI9341::hline(int x0, int x1, int y, int color)
dreschpe 0:da1bf437cbc1 410 {
dreschpe 0:da1bf437cbc1 411 int w;
dreschpe 0:da1bf437cbc1 412 w = x1 - x0 + 1;
dreschpe 0:da1bf437cbc1 413 window(x0,y,w,1);
dreschpe 5:55aed13f2630 414 wr_cmd(0x2C); // send pixel
dreschpe 5:55aed13f2630 415 #if defined TARGET_KL25Z // 8 Bit SPI
dreschpe 5:55aed13f2630 416 int j;
dreschpe 5:55aed13f2630 417 for (j=0; j<w; j++) {
dreschpe 5:55aed13f2630 418 _spi.write(color >> 8);
dreschpe 5:55aed13f2630 419 _spi.write(color & 0xff);
dreschpe 5:55aed13f2630 420 }
dreschpe 5:55aed13f2630 421 #else
dreschpe 0:da1bf437cbc1 422 _spi.format(16,3); // switch to 16 bit Mode 3
dreschpe 0:da1bf437cbc1 423 int j;
dreschpe 0:da1bf437cbc1 424 for (j=0; j<w; j++) {
dreschpe 0:da1bf437cbc1 425 _spi.write(color);
dreschpe 0:da1bf437cbc1 426 }
dreschpe 5:55aed13f2630 427 _spi.format(8,3);
dreschpe 5:55aed13f2630 428 #endif
dreschpe 0:da1bf437cbc1 429 _cs = 1;
dreschpe 0:da1bf437cbc1 430 WindowMax();
dreschpe 0:da1bf437cbc1 431 return;
dreschpe 0:da1bf437cbc1 432 }
dreschpe 0:da1bf437cbc1 433
dreschpe 0:da1bf437cbc1 434 void SPI_TFT_ILI9341::vline(int x, int y0, int y1, int color)
dreschpe 0:da1bf437cbc1 435 {
dreschpe 0:da1bf437cbc1 436 int h;
dreschpe 0:da1bf437cbc1 437 h = y1 - y0 + 1;
dreschpe 0:da1bf437cbc1 438 window(x,y0,1,h);
dreschpe 5:55aed13f2630 439 wr_cmd(0x2C); // send pixel
dreschpe 5:55aed13f2630 440 #if defined TARGET_KL25Z // 8 Bit SPI
dreschpe 5:55aed13f2630 441 for (int y=0; y<h; y++) {
dreschpe 5:55aed13f2630 442 _spi.write(color >> 8);
dreschpe 5:55aed13f2630 443 _spi.write(color & 0xff);
dreschpe 5:55aed13f2630 444 }
dreschpe 5:55aed13f2630 445 #else
dreschpe 0:da1bf437cbc1 446 _spi.format(16,3); // switch to 16 bit Mode 3
dreschpe 0:da1bf437cbc1 447 for (int y=0; y<h; y++) {
dreschpe 0:da1bf437cbc1 448 _spi.write(color);
dreschpe 0:da1bf437cbc1 449 }
dreschpe 5:55aed13f2630 450 _spi.format(8,3);
dreschpe 5:55aed13f2630 451 #endif
dreschpe 0:da1bf437cbc1 452 _cs = 1;
dreschpe 0:da1bf437cbc1 453 WindowMax();
dreschpe 0:da1bf437cbc1 454 return;
dreschpe 0:da1bf437cbc1 455 }
dreschpe 0:da1bf437cbc1 456
dreschpe 0:da1bf437cbc1 457
dreschpe 0:da1bf437cbc1 458
dreschpe 0:da1bf437cbc1 459 void SPI_TFT_ILI9341::line(int x0, int y0, int x1, int y1, int color)
dreschpe 0:da1bf437cbc1 460 {
dreschpe 0:da1bf437cbc1 461 //WindowMax();
dreschpe 0:da1bf437cbc1 462 int dx = 0, dy = 0;
dreschpe 0:da1bf437cbc1 463 int dx_sym = 0, dy_sym = 0;
dreschpe 0:da1bf437cbc1 464 int dx_x2 = 0, dy_x2 = 0;
dreschpe 0:da1bf437cbc1 465 int di = 0;
dreschpe 0:da1bf437cbc1 466
dreschpe 0:da1bf437cbc1 467 dx = x1-x0;
dreschpe 0:da1bf437cbc1 468 dy = y1-y0;
dreschpe 0:da1bf437cbc1 469
dreschpe 0:da1bf437cbc1 470 if (dx == 0) { /* vertical line */
dreschpe 0:da1bf437cbc1 471 if (y1 > y0) vline(x0,y0,y1,color);
dreschpe 0:da1bf437cbc1 472 else vline(x0,y1,y0,color);
dreschpe 0:da1bf437cbc1 473 return;
dreschpe 0:da1bf437cbc1 474 }
dreschpe 0:da1bf437cbc1 475
dreschpe 0:da1bf437cbc1 476 if (dx > 0) {
dreschpe 0:da1bf437cbc1 477 dx_sym = 1;
dreschpe 0:da1bf437cbc1 478 } else {
dreschpe 0:da1bf437cbc1 479 dx_sym = -1;
dreschpe 0:da1bf437cbc1 480 }
dreschpe 0:da1bf437cbc1 481 if (dy == 0) { /* horizontal line */
dreschpe 0:da1bf437cbc1 482 if (x1 > x0) hline(x0,x1,y0,color);
dreschpe 0:da1bf437cbc1 483 else hline(x1,x0,y0,color);
dreschpe 0:da1bf437cbc1 484 return;
dreschpe 0:da1bf437cbc1 485 }
dreschpe 0:da1bf437cbc1 486
dreschpe 0:da1bf437cbc1 487 if (dy > 0) {
dreschpe 0:da1bf437cbc1 488 dy_sym = 1;
dreschpe 0:da1bf437cbc1 489 } else {
dreschpe 0:da1bf437cbc1 490 dy_sym = -1;
dreschpe 0:da1bf437cbc1 491 }
dreschpe 0:da1bf437cbc1 492
dreschpe 0:da1bf437cbc1 493 dx = dx_sym*dx;
dreschpe 0:da1bf437cbc1 494 dy = dy_sym*dy;
dreschpe 0:da1bf437cbc1 495
dreschpe 0:da1bf437cbc1 496 dx_x2 = dx*2;
dreschpe 0:da1bf437cbc1 497 dy_x2 = dy*2;
dreschpe 0:da1bf437cbc1 498
dreschpe 0:da1bf437cbc1 499 if (dx >= dy) {
dreschpe 0:da1bf437cbc1 500 di = dy_x2 - dx;
dreschpe 0:da1bf437cbc1 501 while (x0 != x1) {
dreschpe 0:da1bf437cbc1 502
dreschpe 0:da1bf437cbc1 503 pixel(x0, y0, color);
dreschpe 0:da1bf437cbc1 504 x0 += dx_sym;
dreschpe 0:da1bf437cbc1 505 if (di<0) {
dreschpe 0:da1bf437cbc1 506 di += dy_x2;
dreschpe 0:da1bf437cbc1 507 } else {
dreschpe 0:da1bf437cbc1 508 di += dy_x2 - dx_x2;
dreschpe 0:da1bf437cbc1 509 y0 += dy_sym;
dreschpe 0:da1bf437cbc1 510 }
dreschpe 0:da1bf437cbc1 511 }
dreschpe 0:da1bf437cbc1 512 pixel(x0, y0, color);
dreschpe 0:da1bf437cbc1 513 } else {
dreschpe 0:da1bf437cbc1 514 di = dx_x2 - dy;
dreschpe 0:da1bf437cbc1 515 while (y0 != y1) {
dreschpe 0:da1bf437cbc1 516 pixel(x0, y0, color);
dreschpe 0:da1bf437cbc1 517 y0 += dy_sym;
dreschpe 0:da1bf437cbc1 518 if (di < 0) {
dreschpe 0:da1bf437cbc1 519 di += dx_x2;
dreschpe 0:da1bf437cbc1 520 } else {
dreschpe 0:da1bf437cbc1 521 di += dx_x2 - dy_x2;
dreschpe 0:da1bf437cbc1 522 x0 += dx_sym;
dreschpe 0:da1bf437cbc1 523 }
dreschpe 0:da1bf437cbc1 524 }
dreschpe 0:da1bf437cbc1 525 pixel(x0, y0, color);
dreschpe 0:da1bf437cbc1 526 }
dreschpe 0:da1bf437cbc1 527 return;
dreschpe 0:da1bf437cbc1 528 }
dreschpe 0:da1bf437cbc1 529
dreschpe 0:da1bf437cbc1 530
dreschpe 0:da1bf437cbc1 531 void SPI_TFT_ILI9341::rect(int x0, int y0, int x1, int y1, int color)
dreschpe 0:da1bf437cbc1 532 {
dreschpe 0:da1bf437cbc1 533
dreschpe 0:da1bf437cbc1 534 if (x1 > x0) hline(x0,x1,y0,color);
dreschpe 0:da1bf437cbc1 535 else hline(x1,x0,y0,color);
dreschpe 0:da1bf437cbc1 536
dreschpe 0:da1bf437cbc1 537 if (y1 > y0) vline(x0,y0,y1,color);
dreschpe 0:da1bf437cbc1 538 else vline(x0,y1,y0,color);
dreschpe 0:da1bf437cbc1 539
dreschpe 0:da1bf437cbc1 540 if (x1 > x0) hline(x0,x1,y1,color);
dreschpe 0:da1bf437cbc1 541 else hline(x1,x0,y1,color);
dreschpe 0:da1bf437cbc1 542
dreschpe 0:da1bf437cbc1 543 if (y1 > y0) vline(x1,y0,y1,color);
dreschpe 0:da1bf437cbc1 544 else vline(x1,y1,y0,color);
dreschpe 0:da1bf437cbc1 545
dreschpe 0:da1bf437cbc1 546 return;
dreschpe 0:da1bf437cbc1 547 }
dreschpe 0:da1bf437cbc1 548
dreschpe 0:da1bf437cbc1 549
dreschpe 0:da1bf437cbc1 550
dreschpe 0:da1bf437cbc1 551 void SPI_TFT_ILI9341::fillrect(int x0, int y0, int x1, int y1, int color)
dreschpe 0:da1bf437cbc1 552 {
dreschpe 0:da1bf437cbc1 553
dreschpe 0:da1bf437cbc1 554 int h = y1 - y0 + 1;
dreschpe 0:da1bf437cbc1 555 int w = x1 - x0 + 1;
dreschpe 0:da1bf437cbc1 556 int pixel = h * w;
dreschpe 0:da1bf437cbc1 557 window(x0,y0,w,h);
dreschpe 0:da1bf437cbc1 558 wr_cmd(0x2C); // send pixel
dreschpe 5:55aed13f2630 559 #if defined TARGET_KL25Z // 8 Bit SPI
dreschpe 5:55aed13f2630 560 for (int p=0; p<pixel; p++) {
dreschpe 5:55aed13f2630 561 _spi.write(color >> 8);
dreschpe 5:55aed13f2630 562 _spi.write(color & 0xff);
dreschpe 5:55aed13f2630 563 }
dreschpe 5:55aed13f2630 564 #else
dreschpe 0:da1bf437cbc1 565 _spi.format(16,3); // switch to 16 bit Mode 3
dreschpe 0:da1bf437cbc1 566 for (int p=0; p<pixel; p++) {
dreschpe 0:da1bf437cbc1 567 _spi.write(color);
dreschpe 0:da1bf437cbc1 568 }
dreschpe 5:55aed13f2630 569 _spi.format(8,3);
dreschpe 5:55aed13f2630 570 #endif
dreschpe 0:da1bf437cbc1 571 _cs = 1;
dreschpe 0:da1bf437cbc1 572 WindowMax();
dreschpe 0:da1bf437cbc1 573 return;
dreschpe 0:da1bf437cbc1 574 }
dreschpe 0:da1bf437cbc1 575
dreschpe 0:da1bf437cbc1 576
dreschpe 0:da1bf437cbc1 577 void SPI_TFT_ILI9341::locate(int x, int y)
dreschpe 0:da1bf437cbc1 578 {
dreschpe 0:da1bf437cbc1 579 char_x = x;
dreschpe 0:da1bf437cbc1 580 char_y = y;
dreschpe 0:da1bf437cbc1 581 }
dreschpe 0:da1bf437cbc1 582
dreschpe 0:da1bf437cbc1 583
dreschpe 0:da1bf437cbc1 584
dreschpe 0:da1bf437cbc1 585 int SPI_TFT_ILI9341::columns()
dreschpe 0:da1bf437cbc1 586 {
dreschpe 0:da1bf437cbc1 587 return width() / font[1];
dreschpe 0:da1bf437cbc1 588 }
dreschpe 0:da1bf437cbc1 589
dreschpe 0:da1bf437cbc1 590
dreschpe 0:da1bf437cbc1 591
dreschpe 0:da1bf437cbc1 592 int SPI_TFT_ILI9341::rows()
dreschpe 0:da1bf437cbc1 593 {
dreschpe 0:da1bf437cbc1 594 return height() / font[2];
dreschpe 0:da1bf437cbc1 595 }
dreschpe 0:da1bf437cbc1 596
dreschpe 0:da1bf437cbc1 597
dreschpe 0:da1bf437cbc1 598
dreschpe 0:da1bf437cbc1 599 int SPI_TFT_ILI9341::_putc(int value)
dreschpe 0:da1bf437cbc1 600 {
dreschpe 0:da1bf437cbc1 601 if (value == '\n') { // new line
dreschpe 0:da1bf437cbc1 602 char_x = 0;
dreschpe 0:da1bf437cbc1 603 char_y = char_y + font[2];
dreschpe 0:da1bf437cbc1 604 if (char_y >= height() - font[2]) {
dreschpe 0:da1bf437cbc1 605 char_y = 0;
dreschpe 0:da1bf437cbc1 606 }
dreschpe 0:da1bf437cbc1 607 } else {
dreschpe 0:da1bf437cbc1 608 character(char_x, char_y, value);
dreschpe 0:da1bf437cbc1 609 }
dreschpe 0:da1bf437cbc1 610 return value;
dreschpe 0:da1bf437cbc1 611 }
dreschpe 0:da1bf437cbc1 612
dreschpe 0:da1bf437cbc1 613
dreschpe 0:da1bf437cbc1 614 void SPI_TFT_ILI9341::character(int x, int y, int c)
dreschpe 0:da1bf437cbc1 615 {
dreschpe 0:da1bf437cbc1 616 unsigned int hor,vert,offset,bpl,j,i,b;
dreschpe 0:da1bf437cbc1 617 unsigned char* zeichen;
dreschpe 0:da1bf437cbc1 618 unsigned char z,w;
dreschpe 0:da1bf437cbc1 619
dreschpe 0:da1bf437cbc1 620 if ((c < 31) || (c > 127)) return; // test char range
dreschpe 0:da1bf437cbc1 621
dreschpe 0:da1bf437cbc1 622 // read font parameter from start of array
dreschpe 0:da1bf437cbc1 623 offset = font[0]; // bytes / char
dreschpe 0:da1bf437cbc1 624 hor = font[1]; // get hor size of font
dreschpe 0:da1bf437cbc1 625 vert = font[2]; // get vert size of font
dreschpe 0:da1bf437cbc1 626 bpl = font[3]; // bytes per line
dreschpe 0:da1bf437cbc1 627
dreschpe 0:da1bf437cbc1 628 if (char_x + hor > width()) {
dreschpe 0:da1bf437cbc1 629 char_x = 0;
dreschpe 0:da1bf437cbc1 630 char_y = char_y + vert;
dreschpe 0:da1bf437cbc1 631 if (char_y >= height() - font[2]) {
dreschpe 0:da1bf437cbc1 632 char_y = 0;
dreschpe 0:da1bf437cbc1 633 }
dreschpe 0:da1bf437cbc1 634 }
dreschpe 0:da1bf437cbc1 635 window(char_x, char_y,hor,vert); // char box
dreschpe 5:55aed13f2630 636 wr_cmd(0x2C); // send pixel
dreschpe 5:55aed13f2630 637 #ifndef TARGET_KL25Z // 16 Bit SPI
dreschpe 5:55aed13f2630 638 _spi.format(16,3);
dreschpe 5:55aed13f2630 639 #endif // switch to 16 bit Mode 3
dreschpe 0:da1bf437cbc1 640 zeichen = &font[((c -32) * offset) + 4]; // start of char bitmap
dreschpe 0:da1bf437cbc1 641 w = zeichen[0]; // width of actual char
dreschpe 0:da1bf437cbc1 642 for (j=0; j<vert; j++) { // vert line
dreschpe 0:da1bf437cbc1 643 for (i=0; i<hor; i++) { // horz line
dreschpe 0:da1bf437cbc1 644 z = zeichen[bpl * i + ((j & 0xF8) >> 3)+1];
dreschpe 0:da1bf437cbc1 645 b = 1 << (j & 0x07);
dreschpe 0:da1bf437cbc1 646 if (( z & b ) == 0x00) {
dreschpe 5:55aed13f2630 647 #ifndef TARGET_KL25Z // 16 Bit SPI
dreschpe 0:da1bf437cbc1 648 _spi.write(_background);
dreschpe 5:55aed13f2630 649 #else
dreschpe 5:55aed13f2630 650 _spi.write(_background >> 8);
dreschpe 5:55aed13f2630 651 _spi.write(_background & 0xff);
dreschpe 5:55aed13f2630 652 #endif
dreschpe 0:da1bf437cbc1 653 } else {
dreschpe 5:55aed13f2630 654 #ifndef TARGET_KL25Z // 16 Bit SPI
dreschpe 0:da1bf437cbc1 655 _spi.write(_foreground);
dreschpe 5:55aed13f2630 656 #else
dreschpe 5:55aed13f2630 657 _spi.write(_foreground >> 8);
dreschpe 5:55aed13f2630 658 _spi.write(_foreground & 0xff);
dreschpe 5:55aed13f2630 659 #endif
dreschpe 0:da1bf437cbc1 660 }
dreschpe 0:da1bf437cbc1 661 }
dreschpe 0:da1bf437cbc1 662 }
dreschpe 0:da1bf437cbc1 663 _cs = 1;
dreschpe 5:55aed13f2630 664 #ifndef TARGET_KL25Z // 16 Bit SPI
dreschpe 0:da1bf437cbc1 665 _spi.format(8,3);
dreschpe 5:55aed13f2630 666 #endif
dreschpe 0:da1bf437cbc1 667 WindowMax();
dreschpe 0:da1bf437cbc1 668 if ((w + 2) < hor) { // x offset to next char
dreschpe 0:da1bf437cbc1 669 char_x += w + 2;
dreschpe 0:da1bf437cbc1 670 } else char_x += hor;
dreschpe 0:da1bf437cbc1 671 }
dreschpe 0:da1bf437cbc1 672
dreschpe 0:da1bf437cbc1 673
dreschpe 0:da1bf437cbc1 674 void SPI_TFT_ILI9341::set_font(unsigned char* f)
dreschpe 0:da1bf437cbc1 675 {
dreschpe 0:da1bf437cbc1 676 font = f;
dreschpe 0:da1bf437cbc1 677 }
dreschpe 0:da1bf437cbc1 678
dreschpe 0:da1bf437cbc1 679
dreschpe 0:da1bf437cbc1 680
dreschpe 0:da1bf437cbc1 681 void SPI_TFT_ILI9341::Bitmap(unsigned int x, unsigned int y, unsigned int w, unsigned int h,unsigned char *bitmap)
dreschpe 0:da1bf437cbc1 682 {
dreschpe 0:da1bf437cbc1 683 unsigned int j;
dreschpe 0:da1bf437cbc1 684 int padd;
dreschpe 0:da1bf437cbc1 685 unsigned short *bitmap_ptr = (unsigned short *)bitmap;
dreschpe 5:55aed13f2630 686 #if defined TARGET_KL25Z // 8 Bit SPI
dreschpe 5:55aed13f2630 687 unsigned short pix_temp;
dreschpe 5:55aed13f2630 688 #endif
dreschpe 5:55aed13f2630 689
dreschpe 2:0a16083193a4 690 unsigned int i;
dreschpe 2:0a16083193a4 691
dreschpe 0:da1bf437cbc1 692 // the lines are padded to multiple of 4 bytes in a bitmap
dreschpe 0:da1bf437cbc1 693 padd = -1;
dreschpe 0:da1bf437cbc1 694 do {
dreschpe 0:da1bf437cbc1 695 padd ++;
dreschpe 0:da1bf437cbc1 696 } while (2*(w + padd)%4 != 0);
dreschpe 0:da1bf437cbc1 697 window(x, y, w, h);
dreschpe 2:0a16083193a4 698 bitmap_ptr += ((h - 1)* (w + padd));
dreschpe 5:55aed13f2630 699 wr_cmd(0x2C); // send pixel
dreschpe 5:55aed13f2630 700 #ifndef TARGET_KL25Z // 16 Bit SPI
dreschpe 5:55aed13f2630 701 _spi.format(16,3);
dreschpe 5:55aed13f2630 702 #endif // switch to 16 bit Mode 3
dreschpe 2:0a16083193a4 703 for (j = 0; j < h; j++) { //Lines
dreschpe 2:0a16083193a4 704 for (i = 0; i < w; i++) { // one line
dreschpe 5:55aed13f2630 705 #if defined TARGET_KL25Z // 8 Bit SPI
dreschpe 5:55aed13f2630 706 pix_temp = *bitmap_ptr;
dreschpe 5:55aed13f2630 707 _spi.write(pix_temp >> 8);
dreschpe 5:55aed13f2630 708 _spi.write(pix_temp);
dreschpe 5:55aed13f2630 709 bitmap_ptr++;
dreschpe 5:55aed13f2630 710 #else
dreschpe 5:55aed13f2630 711 _spi.write(*bitmap_ptr); // one line
dreschpe 5:55aed13f2630 712 bitmap_ptr++;
dreschpe 5:55aed13f2630 713 #endif
dreschpe 0:da1bf437cbc1 714 }
dreschpe 0:da1bf437cbc1 715 bitmap_ptr -= 2*w;
dreschpe 0:da1bf437cbc1 716 bitmap_ptr -= padd;
dreschpe 0:da1bf437cbc1 717 }
dreschpe 0:da1bf437cbc1 718 _cs = 1;
dreschpe 5:55aed13f2630 719 #ifndef TARGET_KL25Z // 16 Bit SPI
dreschpe 0:da1bf437cbc1 720 _spi.format(8,3);
dreschpe 5:55aed13f2630 721 #endif
dreschpe 0:da1bf437cbc1 722 WindowMax();
dreschpe 0:da1bf437cbc1 723 }
dreschpe 0:da1bf437cbc1 724
dreschpe 0:da1bf437cbc1 725
dreschpe 6:fe07ae8329f7 726 // local filesystem is not implemented in kinetis board , but you can add a SD card
dreschpe 5:55aed13f2630 727
dreschpe 0:da1bf437cbc1 728 int SPI_TFT_ILI9341::BMP_16(unsigned int x, unsigned int y, const char *Name_BMP)
dreschpe 0:da1bf437cbc1 729 {
dreschpe 0:da1bf437cbc1 730
dreschpe 0:da1bf437cbc1 731 #define OffsetPixelWidth 18
dreschpe 0:da1bf437cbc1 732 #define OffsetPixelHeigh 22
dreschpe 0:da1bf437cbc1 733 #define OffsetFileSize 34
dreschpe 0:da1bf437cbc1 734 #define OffsetPixData 10
dreschpe 0:da1bf437cbc1 735 #define OffsetBPP 28
dreschpe 0:da1bf437cbc1 736
dreschpe 0:da1bf437cbc1 737 char filename[50];
dreschpe 0:da1bf437cbc1 738 unsigned char BMP_Header[54];
dreschpe 0:da1bf437cbc1 739 unsigned short BPP_t;
dreschpe 0:da1bf437cbc1 740 unsigned int PixelWidth,PixelHeigh,start_data;
dreschpe 0:da1bf437cbc1 741 unsigned int i,off;
dreschpe 0:da1bf437cbc1 742 int padd,j;
dreschpe 0:da1bf437cbc1 743 unsigned short *line;
dreschpe 0:da1bf437cbc1 744
dreschpe 0:da1bf437cbc1 745 // get the filename
dreschpe 6:fe07ae8329f7 746 i=0;
dreschpe 0:da1bf437cbc1 747 while (*Name_BMP!='\0') {
dreschpe 0:da1bf437cbc1 748 filename[i++]=*Name_BMP++;
dreschpe 0:da1bf437cbc1 749 }
dreschpe 6:fe07ae8329f7 750 filename[i] = 0;
dreschpe 6:fe07ae8329f7 751
dreschpe 0:da1bf437cbc1 752 FILE *Image = fopen((const char *)&filename[0], "rb"); // open the bmp file
dreschpe 0:da1bf437cbc1 753 if (!Image) {
dreschpe 0:da1bf437cbc1 754 return(0); // error file not found !
dreschpe 0:da1bf437cbc1 755 }
dreschpe 0:da1bf437cbc1 756
dreschpe 0:da1bf437cbc1 757 fread(&BMP_Header[0],1,54,Image); // get the BMP Header
dreschpe 0:da1bf437cbc1 758
dreschpe 0:da1bf437cbc1 759 if (BMP_Header[0] != 0x42 || BMP_Header[1] != 0x4D) { // check magic byte
dreschpe 0:da1bf437cbc1 760 fclose(Image);
dreschpe 0:da1bf437cbc1 761 return(-1); // error no BMP file
dreschpe 0:da1bf437cbc1 762 }
dreschpe 0:da1bf437cbc1 763
dreschpe 0:da1bf437cbc1 764 BPP_t = BMP_Header[OffsetBPP] + (BMP_Header[OffsetBPP + 1] << 8);
dreschpe 0:da1bf437cbc1 765 if (BPP_t != 0x0010) {
dreschpe 0:da1bf437cbc1 766 fclose(Image);
dreschpe 0:da1bf437cbc1 767 return(-2); // error no 16 bit BMP
dreschpe 0:da1bf437cbc1 768 }
dreschpe 0:da1bf437cbc1 769
dreschpe 0:da1bf437cbc1 770 PixelHeigh = BMP_Header[OffsetPixelHeigh] + (BMP_Header[OffsetPixelHeigh + 1] << 8) + (BMP_Header[OffsetPixelHeigh + 2] << 16) + (BMP_Header[OffsetPixelHeigh + 3] << 24);
dreschpe 0:da1bf437cbc1 771 PixelWidth = BMP_Header[OffsetPixelWidth] + (BMP_Header[OffsetPixelWidth + 1] << 8) + (BMP_Header[OffsetPixelWidth + 2] << 16) + (BMP_Header[OffsetPixelWidth + 3] << 24);
dreschpe 0:da1bf437cbc1 772 if (PixelHeigh > height() + y || PixelWidth > width() + x) {
dreschpe 0:da1bf437cbc1 773 fclose(Image);
dreschpe 0:da1bf437cbc1 774 return(-3); // to big
dreschpe 0:da1bf437cbc1 775 }
dreschpe 0:da1bf437cbc1 776
dreschpe 0:da1bf437cbc1 777 start_data = BMP_Header[OffsetPixData] + (BMP_Header[OffsetPixData + 1] << 8) + (BMP_Header[OffsetPixData + 2] << 16) + (BMP_Header[OffsetPixData + 3] << 24);
dreschpe 0:da1bf437cbc1 778
dreschpe 0:da1bf437cbc1 779 line = (unsigned short *) malloc (2 * PixelWidth); // we need a buffer for a line
dreschpe 0:da1bf437cbc1 780 if (line == NULL) {
dreschpe 0:da1bf437cbc1 781 return(-4); // error no memory
dreschpe 0:da1bf437cbc1 782 }
dreschpe 0:da1bf437cbc1 783
dreschpe 0:da1bf437cbc1 784 // the bmp lines are padded to multiple of 4 bytes
dreschpe 0:da1bf437cbc1 785 padd = -1;
dreschpe 0:da1bf437cbc1 786 do {
dreschpe 0:da1bf437cbc1 787 padd ++;
dreschpe 0:da1bf437cbc1 788 } while ((PixelWidth * 2 + padd)%4 != 0);
dreschpe 0:da1bf437cbc1 789
dreschpe 0:da1bf437cbc1 790 window(x, y,PixelWidth ,PixelHeigh);
dreschpe 6:fe07ae8329f7 791 wr_cmd(0x2C); // send pixel
dreschpe 6:fe07ae8329f7 792 #ifndef TARGET_KL25Z // only 8 Bit SPI
dreschpe 6:fe07ae8329f7 793 _spi.format(16,3);
dreschpe 6:fe07ae8329f7 794 #endif // switch to 16 bit Mode 3
dreschpe 0:da1bf437cbc1 795 for (j = PixelHeigh - 1; j >= 0; j--) { //Lines bottom up
dreschpe 0:da1bf437cbc1 796 off = j * (PixelWidth * 2 + padd) + start_data; // start of line
dreschpe 0:da1bf437cbc1 797 fseek(Image, off ,SEEK_SET);
dreschpe 6:fe07ae8329f7 798 fread(line,1,PixelWidth * 2,Image); // read a line - slow
dreschpe 0:da1bf437cbc1 799 for (i = 0; i < PixelWidth; i++) { // copy pixel data to TFT
dreschpe 6:fe07ae8329f7 800 #ifndef TARGET_KL25Z // only 8 Bit SPI
dreschpe 0:da1bf437cbc1 801 _spi.write(line[i]); // one 16 bit pixel
dreschpe 6:fe07ae8329f7 802 #else
dreschpe 6:fe07ae8329f7 803 _spi.write(line[i] >> 8);
dreschpe 6:fe07ae8329f7 804 _spi.write(line[i]);
dreschpe 6:fe07ae8329f7 805 #endif
dreschpe 0:da1bf437cbc1 806 }
dreschpe 0:da1bf437cbc1 807 }
dreschpe 0:da1bf437cbc1 808 _cs = 1;
dreschpe 0:da1bf437cbc1 809 _spi.format(8,3);
dreschpe 0:da1bf437cbc1 810 free (line);
dreschpe 0:da1bf437cbc1 811 fclose(Image);
dreschpe 0:da1bf437cbc1 812 WindowMax();
dreschpe 0:da1bf437cbc1 813 return(1);
dreschpe 5:55aed13f2630 814 }