|
| 1 | +' ST7789 - TFT controller |
| 2 | +' ============================= |
| 3 | +' |
| 4 | +' This example demonstrates how to drive a TFT display with a ST7789 controller. |
| 5 | +' With the current IOIO implementation the example works but is unusable slow. |
| 6 | +' ---------------------------------- |
| 7 | +' There exist many TFT displays using the ST7789 controller. This examples is written |
| 8 | +' for the Waveshare 1.3inch LCD module with 240x240 pixels. With some minor modification |
| 9 | +' especially for the pins, TFTs from other manufacturers should also work. Be carefull |
| 10 | +' with VCC. If you are using a bare TFT, then drive it only with 3.3V. Many breakout |
| 11 | +' boards (i.e. Adafruit) support 5V. |
| 12 | +' |
| 13 | +' ------- ------ |
| 14 | +' IOIO | |TFT |
| 15 | +' PIN 40|-------|DIN (MOSI) |
| 16 | +' PIN 39|-------|CLK (SCL) |
| 17 | +' PIN 38|-------|CS |
| 18 | +' PIN 37|-------|DC |
| 19 | +' PIN 36|-------|RST |
| 20 | +' PIN 35|-------|BL |
| 21 | +' GND |-------|GND |
| 22 | +' 5V |-------|VIN |
| 23 | +'-------- ------ |
| 24 | + |
| 25 | +' This example is based on the C library for Arduino: |
| 26 | +' https://github.com/cbm80amiga/Arduino_ST7789_Fast/blob/master/Arduino_ST7789_Fast.cpp |
| 27 | +' ------------------------------------------------------------------------------------- |
| 28 | + |
| 29 | +import ioio |
| 30 | + |
| 31 | +const MISO = 34 ' SPI MISO (unused) |
| 32 | +const DIN = 40 ' SPI MOSI |
| 33 | +const CLK = 39 ' SPI clock |
| 34 | +const CS = 38 ' SPI Chip select |
| 35 | +const DC = 37 ' Data or command -> HIGH = data / LOW = command |
| 36 | +const RST = 36 ' Chip reset |
| 37 | +const BL = 35 ' Blacklight control |
| 38 | + |
| 39 | +const ST7789_NOP = 0x00 |
| 40 | +const ST7789_SWRESET = 0x01 |
| 41 | +const ST7789_SLPOUT = 0x11 |
| 42 | +const ST7789_NORON = 0x13 |
| 43 | +const ST7789_INVON = 0x21 |
| 44 | +const ST7789_DISPON = 0x29 |
| 45 | +const ST7789_CASET = 0x2A |
| 46 | +const ST7789_RASET = 0x2B |
| 47 | +const ST7789_RAMWR = 0x2C |
| 48 | +const ST7789_COLMOD = 0x3A |
| 49 | +const ST7789_MADCTL = 0x36 |
| 50 | +const ST7789_MADCTL_MY = 0x80 |
| 51 | +const ST7789_MADCTL_MX = 0x40 |
| 52 | +const ST7789_MADCTL_MV = 0x20 |
| 53 | +const ST7789_MADCTL_ML = 0x10 |
| 54 | +const ST7789_MADCTL_RGB = 0x00 |
| 55 | +const ST7789_240x240_XSTART = 0 |
| 56 | +const ST7789_240x240_YSTART = 0 |
| 57 | +const ST7789_TFTWIDTH = 240 |
| 58 | +const ST7789_TFTHEIGHT = 240 |
| 59 | + |
| 60 | +const BLACK = 0x0000 |
| 61 | +const BLUE = 0x001F |
| 62 | +const RED = 0xF800 |
| 63 | +const GREEN = 0x07E0 |
| 64 | +const CYAN = 0x07FF |
| 65 | +const MAGENTA = 0xF81F |
| 66 | +const YELLOW = 0xFFE0 |
| 67 | +const WHITE = 0xFFFF |
| 68 | + |
| 69 | +const HIGH = TRUE |
| 70 | +const LOW = FALSE |
| 71 | +const PIN_DELAY = 1 |
| 72 | + |
| 73 | +colstart = 0 |
| 74 | +rowstart = 0 |
| 75 | +ystart = 0 |
| 76 | +xstart = 0 |
| 77 | +width = 240 |
| 78 | +height = 240 |
| 79 | + |
| 80 | +Setup(240, 240) ' parameter: TFT width , TFT height |
| 81 | +FillScreen(GREEN) |
| 82 | + |
| 83 | +'for xx = 100 to 150 |
| 84 | +' DrawPixel(xx, 100, RGBto565(255, 0, 255)) |
| 85 | +'next |
| 86 | + |
| 87 | +print "done" |
| 88 | + |
| 89 | +'######################################## |
| 90 | + |
| 91 | +sub Setup(w, h) |
| 92 | + Print "Connect to TFT" |
| 93 | + SPI = ioio.openSpiMaster(MISO, DIN, CLK, CS) |
| 94 | + ResetPin = ioio.openDigitalOutput(RST) |
| 95 | + DCPin = ioio.openDigitalOutput(DC) |
| 96 | + BLPin = ioio.openDigitalOutput(BL) |
| 97 | + ioio.waitForConnect(10) |
| 98 | + Print "Connection established" |
| 99 | + |
| 100 | + if(w == 240 and h == 240) then rowstart = 80 |
| 101 | + width = w |
| 102 | + height = h |
| 103 | + |
| 104 | + ' Background light on |
| 105 | + BLPin.write(HIGH) |
| 106 | + |
| 107 | + ' Hardware reset |
| 108 | + ResetPin.write(HIGH) |
| 109 | + delay(50) |
| 110 | + ResetPin.write(LOW) |
| 111 | + delay(50) |
| 112 | + ResetPin.write(HIGH) |
| 113 | + delay(150) |
| 114 | + |
| 115 | + 'Init |
| 116 | + writeCmd(ST7789_SWRESET) : delay(150) |
| 117 | + writeCmd(ST7789_SLPOUT) : delay(500) |
| 118 | + writeCmd(ST7789_COLMOD) : writeData8(0x55) : delay(10) ' RGB565 |
| 119 | + writeCmd(ST7789_MADCTL) : writeData8(0x00) |
| 120 | + writeCmd(ST7789_CASET) : writeData16(ST7789_240x240_XSTART) : writeData16(ST7789_TFTWIDTH + ST7789_240x240_XSTART) |
| 121 | + writeCmd(ST7789_RASET) : writeData16(ST7789_240x240_YSTART) : writeData16(ST7789_TFTHEIGHT + ST7789_240x240_YSTART) |
| 122 | + writeCmd(ST7789_INVON) : delay(10) |
| 123 | + writeCmd(ST7789_NORON) : delay(10) |
| 124 | + writeCmd(ST7789_DISPON) : delay(10) |
| 125 | + |
| 126 | + SetRotation(2) |
| 127 | +end |
| 128 | + |
| 129 | +func RGBto565(r,g,b) |
| 130 | + return ((((r) BAND 0xF8) lshift 8) BOR (((g) BAND 0xFC) lshift 3) BOR ((b) rshift 3)) |
| 131 | +end |
| 132 | + |
| 133 | +sub WriteCmd( c) |
| 134 | + DCPin.write(LOW) |
| 135 | + delay(PIN_DELAY) |
| 136 | + SPI.write(c, ST7789_NOP) |
| 137 | +end |
| 138 | + |
| 139 | +sub WriteData8(Data_Uint8) |
| 140 | + DCPin.write(HIGH) |
| 141 | + delay(PIN_DELAY) |
| 142 | + SPI.write(Data_Uint8, 0) |
| 143 | +end |
| 144 | + |
| 145 | +sub WriteData16(Data_Uint16) |
| 146 | + DCPin.write(HIGH) |
| 147 | + delay(PIN_DELAY) |
| 148 | + SPI.write(Data_Uint16 rshift 8, Data_Uint16 BAND 0xFF) |
| 149 | +end |
| 150 | + |
| 151 | +sub DrawPixel(x, y, c) |
| 152 | + setAddrWindow(x, y, x + 1, y + 1) |
| 153 | + WriteCmd(ST7789_RAMWR) |
| 154 | + writeData16(c) |
| 155 | +end |
| 156 | + |
| 157 | +sub FillRect(x, y, w, h, col) |
| 158 | + if(x >= width OR y >= height OR w <= 0 OR h <= 0) then return |
| 159 | + if(x + w - 1 >= width) then w = width - x |
| 160 | + if(y + h - 1 >= height) then h = height - y |
| 161 | + |
| 162 | + setAddrWindow(x, y, x + w - 1, y + h - 1) |
| 163 | + WriteCmd(ST7789_RAMWR) |
| 164 | + |
| 165 | + DCPin.write(HIGH) |
| 166 | + delay(PIN_DELAY) |
| 167 | + num = w * h |
| 168 | + c_high = col rshift 8 |
| 169 | + c_low = col BAND 0xFF |
| 170 | + while(num) |
| 171 | + num-- |
| 172 | + SPI.write(c_high, c_low) |
| 173 | + wend |
| 174 | +end |
| 175 | + |
| 176 | +sub FillScreen(col) |
| 177 | + FillRect(0, 0, width, height, col) |
| 178 | +end |
| 179 | + |
| 180 | +sub SetRotation(m) |
| 181 | + writeCmd(ST7789_MADCTL) |
| 182 | + rotation = m BAND 3 |
| 183 | + select case rotation |
| 184 | + case 0 |
| 185 | + writeData8(ST7789_MADCTL_MX BOR ST7789_MADCTL_MY BOR ST7789_MADCTL_RGB) |
| 186 | + xstart = colstart |
| 187 | + ystart = rowstart |
| 188 | + case 1 |
| 189 | + writeData8(ST7789_MADCTL_MY BOR ST7789_MADCTL_MV BOR ST7789_MADCTL_RGB) |
| 190 | + ystart = colstart |
| 191 | + xstart = rowstart |
| 192 | + case 2 |
| 193 | + writeData8(ST7789_MADCTL_RGB) |
| 194 | + xstart = 0 |
| 195 | + ystart = 0 |
| 196 | + case 3 |
| 197 | + writeData8(ST7789_MADCTL_MX BOR ST7789_MADCTL_MV BOR ST7789_MADCTL_RGB) |
| 198 | + xstart = 0 |
| 199 | + ystart = 0 |
| 200 | + end select |
| 201 | +end |
| 202 | + |
| 203 | + |
| 204 | +sub setAddrWindow(xs, xe, ys, ye) |
| 205 | + xs += xstart |
| 206 | + xe += xstart |
| 207 | + ys += ystart |
| 208 | + ye += ystart |
| 209 | + |
| 210 | + 'CASET |
| 211 | + WriteCmd(ST77XX_CASET) |
| 212 | + DCPin.write(HIGH) ' data (active high) |
| 213 | + SPI.write(xs rshift 8, xs BAND 0xFF) |
| 214 | + SPI.write(xe rshift 8, xe BAND 0xFF) |
| 215 | + ' RASET |
| 216 | + WriteCmd(ST77XX_RASET) |
| 217 | + DCPin.write(HIGH) ' data (active high) |
| 218 | + SPI.write(ys rshift 8, ys BAND 0xFF) |
| 219 | + SPI.write(ye rshift 8, ye BAND 0xFF) |
| 220 | +end |
0 commit comments