acidportal- 😈 Worlds smallest Evil Portal on a LilyGo T-QT |
git clone git://git.acid.vegas/acidportal.git |
Log | Files | Refs | Archive | README | LICENSE |
TFT_eSPI_ESP32.h (22115B)
1 //////////////////////////////////////////////////// 2 // TFT_eSPI driver functions for ESP32 processors // 3 //////////////////////////////////////////////////// 4 5 #ifndef _TFT_eSPI_ESP32H_ 6 #define _TFT_eSPI_ESP32H_ 7 8 // Processor ID reported by getSetup() 9 #define PROCESSOR_ID 0x32 10 11 // Include processor specific header 12 #include "soc/spi_reg.h" 13 #include "driver/spi_master.h" 14 15 #if !defined(CONFIG_IDF_TARGET_ESP32C3) && !defined(CONFIG_IDF_TARGET_ESP32S2) && !defined(CONFIG_IDF_TARGET_ESP32) 16 #define CONFIG_IDF_TARGET_ESP32 17 #endif 18 19 // Fix IDF problems with ESP32C3 20 #if CONFIG_IDF_TARGET_ESP32C3 21 // Fix ESP32C3 IDF bug for missing definition 22 #ifndef REG_SPI_BASE 23 #define REG_SPI_BASE(i) (DR_REG_SPI1_BASE + (((i)>1) ? (((i)* 0x1000) + 0x20000) : (((~(i)) & 1)* 0x1000 ))) 24 #endif 25 26 // Fix ESP32C3 IDF bug for name change 27 #ifndef SPI_MOSI_DLEN_REG 28 #define SPI_MOSI_DLEN_REG(x) SPI_MS_DLEN_REG(x) 29 #endif 30 31 // Fix ESP32C3 specific register reference 32 #define out_w1tc out_w1tc.val 33 #define out_w1ts out_w1ts.val 34 #endif 35 36 // SUPPORT_TRANSACTIONS is mandatory for ESP32 so the hal mutex is toggled 37 #if !defined (SUPPORT_TRANSACTIONS) 38 #define SUPPORT_TRANSACTIONS 39 #endif 40 41 /* 42 ESP32: 43 FSPI not defined 44 HSPI = 2, uses SPI2 45 VSPI = 3, uses SPI3 46 47 ESP32-S2: 48 FSPI = 1, uses SPI2 49 HSPI = 2, uses SPI3 50 VSPI not defined 51 52 ESP32 C3: 53 FSPI = 0, uses SPI2 ???? To be checked 54 HSPI = 1, uses SPI3 ???? To be checked 55 VSPI not defined 56 57 For ESP32/S2/C3: 58 SPI1_HOST = 0 59 SPI2_HOST = 1 60 SPI3_HOST = 2 61 */ 62 63 // ESP32 specific SPI port selection 64 #ifdef USE_HSPI_PORT 65 #ifdef CONFIG_IDF_TARGET_ESP32 66 #define SPI_PORT HSPI //HSPI is port 2 on ESP32 67 #else 68 #define SPI_PORT 3 //HSPI is port 3 on ESP32 S2 69 #endif 70 #elif defined(USE_FSPI_PORT) 71 #define SPI_PORT 2 //FSPI(ESP32 S2) 72 #else 73 #ifdef CONFIG_IDF_TARGET_ESP32 74 #define SPI_PORT VSPI 75 #else 76 #define SPI_PORT 2 //FSPI(ESP32 S2) 77 #endif 78 #endif 79 80 #ifdef RPI_DISPLAY_TYPE 81 #define CMD_BITS (16-1) 82 #else 83 #define CMD_BITS (8-1) 84 #endif 85 86 // Initialise processor specific SPI functions, used by init() 87 #define INIT_TFT_DATA_BUS // Not used 88 89 // Define a generic flag for 8 bit parallel 90 #if defined (ESP32_PARALLEL) // Specific to ESP32 for backwards compatibility 91 #if !defined (TFT_PARALLEL_8_BIT) 92 #define TFT_PARALLEL_8_BIT // Generic parallel flag 93 #endif 94 #endif 95 96 // Ensure ESP32 specific flag is defined for 8 bit parallel 97 #if defined (TFT_PARALLEL_8_BIT) 98 #if !defined (ESP32_PARALLEL) 99 #define ESP32_PARALLEL 100 #endif 101 #endif 102 103 // Processor specific code used by SPI bus transaction startWrite and endWrite functions 104 #if !defined (ESP32_PARALLEL) 105 #if (TFT_SPI_MODE == SPI_MODE1) || (TFT_SPI_MODE == SPI_MODE2) 106 #define SET_BUS_WRITE_MODE *_spi_user = SPI_USR_MOSI | SPI_CK_OUT_EDGE 107 #define SET_BUS_READ_MODE *_spi_user = SPI_USR_MOSI | SPI_USR_MISO | SPI_DOUTDIN | SPI_CK_OUT_EDGE 108 #else 109 #define SET_BUS_WRITE_MODE *_spi_user = SPI_USR_MOSI 110 #define SET_BUS_READ_MODE *_spi_user = SPI_USR_MOSI | SPI_USR_MISO | SPI_DOUTDIN 111 #endif 112 #else 113 // Not applicable to parallel bus 114 #define SET_BUS_WRITE_MODE 115 #define SET_BUS_READ_MODE 116 #endif 117 118 // Code to check if DMA is busy, used by SPI bus transaction transaction and endWrite functions 119 #if !defined(TFT_PARALLEL_8_BIT) && !defined(SPI_18BIT_DRIVER) 120 #define ESP32_DMA 121 // Code to check if DMA is busy, used by SPI DMA + transaction + endWrite functions 122 #define DMA_BUSY_CHECK dmaWait() 123 #else 124 #define DMA_BUSY_CHECK 125 #endif 126 127 #if defined(TFT_PARALLEL_8_BIT) 128 #define SPI_BUSY_CHECK 129 #else 130 #define SPI_BUSY_CHECK while (*_spi_cmd&SPI_USR) 131 #endif 132 133 // If smooth font is used then it is likely SPIFFS will be needed 134 #ifdef SMOOTH_FONT 135 // Call up the SPIFFS (SPI FLASH Filing System) for the anti-aliased fonts 136 #define FS_NO_GLOBALS 137 #include <FS.h> 138 #include "SPIFFS.h" // ESP32 only 139 #define FONT_FS_AVAILABLE 140 #endif 141 142 143 //////////////////////////////////////////////////////////////////////////////////////// 144 // Define the DC (TFT Data/Command or Register Select (RS))pin drive code 145 //////////////////////////////////////////////////////////////////////////////////////// 146 #ifndef TFT_DC 147 #define DC_C // No macro allocated so it generates no code 148 #define DC_D // No macro allocated so it generates no code 149 #else 150 #if defined (TFT_PARALLEL_8_BIT) 151 // TFT_DC, by design, must be in range 0-31 for single register parallel write 152 #if (TFT_DC >= 0) && (TFT_DC < 32) 153 #define DC_C GPIO.out_w1tc = (1 << TFT_DC) 154 #define DC_D GPIO.out_w1ts = (1 << TFT_DC) 155 #elif (TFT_DC >= 32) 156 #define DC_C GPIO.out1_w1tc.val = (1 << (TFT_DC- 32)) 157 #define DC_D GPIO.out1_w1ts.val = (1 << (TFT_DC- 32)) 158 #else 159 #define DC_C 160 #define DC_D 161 #endif 162 #else 163 #if (TFT_DC >= 32) 164 #ifdef RPI_DISPLAY_TYPE // RPi displays need a slower DC change 165 #define DC_C GPIO.out1_w1ts.val = (1 << (TFT_DC - 32)); \ 166 GPIO.out1_w1tc.val = (1 << (TFT_DC - 32)) 167 #define DC_D GPIO.out1_w1tc.val = (1 << (TFT_DC - 32)); \ 168 GPIO.out1_w1ts.val = (1 << (TFT_DC - 32)) 169 #else 170 #define DC_C GPIO.out1_w1tc.val = (1 << (TFT_DC - 32))//;GPIO.out1_w1tc.val = (1 << (TFT_DC - 32)) 171 #define DC_D GPIO.out1_w1ts.val = (1 << (TFT_DC - 32))//;GPIO.out1_w1ts.val = (1 << (TFT_DC - 32)) 172 #endif 173 #elif (TFT_DC >= 0) 174 #if defined (RPI_DISPLAY_TYPE) 175 #if defined (ILI9486_DRIVER) 176 // RPi ILI9486 display needs a slower DC change 177 #define DC_C GPIO.out_w1tc = (1 << TFT_DC); \ 178 GPIO.out_w1tc = (1 << TFT_DC) 179 #define DC_D GPIO.out_w1tc = (1 << TFT_DC); \ 180 GPIO.out_w1ts = (1 << TFT_DC) 181 #else 182 // Other RPi displays need a slower C->D change 183 #define DC_C GPIO.out_w1tc = (1 << TFT_DC) 184 #define DC_D GPIO.out_w1tc = (1 << TFT_DC); \ 185 GPIO.out_w1ts = (1 << TFT_DC) 186 #endif 187 #else 188 #define DC_C GPIO.out_w1tc = (1 << TFT_DC)//;GPIO.out_w1tc = (1 << TFT_DC) 189 #define DC_D GPIO.out_w1ts = (1 << TFT_DC)//;GPIO.out_w1ts = (1 << TFT_DC) 190 #endif 191 #else 192 #define DC_C 193 #define DC_D 194 #endif 195 #endif 196 #endif 197 198 //////////////////////////////////////////////////////////////////////////////////////// 199 // Define the CS (TFT chip select) pin drive code 200 //////////////////////////////////////////////////////////////////////////////////////// 201 #ifndef TFT_CS 202 #define TFT_CS -1 // Keep DMA code happy 203 #define CS_L // No macro allocated so it generates no code 204 #define CS_H // No macro allocated so it generates no code 205 #else 206 #if defined (TFT_PARALLEL_8_BIT) 207 #if TFT_CS >= 32 208 #define CS_L GPIO.out1_w1tc.val = (1 << (TFT_CS - 32)) 209 #define CS_H GPIO.out1_w1ts.val = (1 << (TFT_CS - 32)) 210 #elif TFT_CS >= 0 211 #define CS_L GPIO.out_w1tc = (1 << TFT_CS) 212 #define CS_H GPIO.out_w1ts = (1 << TFT_CS) 213 #else 214 #define CS_L 215 #define CS_H 216 #endif 217 #else 218 #if (TFT_CS >= 32) 219 #ifdef RPI_DISPLAY_TYPE // RPi display needs a slower CS change 220 #define CS_L GPIO.out1_w1ts.val = (1 << (TFT_CS - 32)); \ 221 GPIO.out1_w1tc.val = (1 << (TFT_CS - 32)) 222 #define CS_H GPIO.out1_w1tc.val = (1 << (TFT_CS - 32)); \ 223 GPIO.out1_w1ts.val = (1 << (TFT_CS - 32)) 224 #else 225 #define CS_L GPIO.out1_w1tc.val = (1 << (TFT_CS - 32)); GPIO.out1_w1tc.val = (1 << (TFT_CS - 32)) 226 #define CS_H GPIO.out1_w1ts.val = (1 << (TFT_CS - 32))//;GPIO.out1_w1ts.val = (1 << (TFT_CS - 32)) 227 #endif 228 #elif (TFT_CS >= 0) 229 #ifdef RPI_DISPLAY_TYPE // RPi display needs a slower CS change 230 #define CS_L GPIO.out_w1ts = (1 << TFT_CS); GPIO.out_w1tc = (1 << TFT_CS) 231 #define CS_H GPIO.out_w1tc = (1 << TFT_CS); GPIO.out_w1ts = (1 << TFT_CS) 232 #else 233 #define CS_L GPIO.out_w1tc = (1 << TFT_CS); GPIO.out_w1tc = (1 << TFT_CS) 234 #define CS_H GPIO.out_w1ts = (1 << TFT_CS)//;GPIO.out_w1ts = (1 << TFT_CS) 235 #endif 236 #else 237 #define CS_L 238 #define CS_H 239 #endif 240 #endif 241 #endif 242 243 //////////////////////////////////////////////////////////////////////////////////////// 244 // Define the WR (TFT Write) pin drive code 245 //////////////////////////////////////////////////////////////////////////////////////// 246 #if defined (TFT_WR) 247 #if (TFT_WR >= 32) 248 // Note: it will be ~1.25x faster if the TFT_WR pin uses a GPIO pin lower than 32 249 #define WR_L GPIO.out1_w1tc.val = (1 << (TFT_WR - 32)) 250 #define WR_H GPIO.out1_w1ts.val = (1 << (TFT_WR - 32)) 251 #elif (TFT_WR >= 0) 252 // TFT_WR, for best performance, should be in range 0-31 for single register parallel write 253 #define WR_L GPIO.out_w1tc = (1 << TFT_WR) 254 #define WR_H GPIO.out_w1ts = (1 << TFT_WR) 255 #else 256 #define WR_L 257 #define WR_H 258 #endif 259 #else 260 #define WR_L 261 #define WR_H 262 #endif 263 264 //////////////////////////////////////////////////////////////////////////////////////// 265 // Define the touch screen chip select pin drive code 266 //////////////////////////////////////////////////////////////////////////////////////// 267 #ifndef TOUCH_CS 268 #define T_CS_L // No macro allocated so it generates no code 269 #define T_CS_H // No macro allocated so it generates no code 270 #else // XPT2046 is slow, so use slower digitalWrite here 271 #define T_CS_L digitalWrite(TOUCH_CS, LOW) 272 #define T_CS_H digitalWrite(TOUCH_CS, HIGH) 273 #endif 274 275 //////////////////////////////////////////////////////////////////////////////////////// 276 // Make sure SPI default pins are assigned if not specified by user or set to -1 277 //////////////////////////////////////////////////////////////////////////////////////// 278 #if !defined (TFT_PARALLEL_8_BIT) 279 280 #ifdef USE_HSPI_PORT 281 282 #ifndef TFT_MISO 283 #define TFT_MISO -1 284 #endif 285 286 #ifndef TFT_MOSI 287 #define TFT_MOSI 13 288 #endif 289 #if (TFT_MOSI == -1) 290 #undef TFT_MOSI 291 #define TFT_MOSI 13 292 #endif 293 294 #ifndef TFT_SCLK 295 #define TFT_SCLK 14 296 #endif 297 #if (TFT_SCLK == -1) 298 #undef TFT_SCLK 299 #define TFT_SCLK 14 300 #endif 301 302 #else // VSPI port 303 304 #ifndef TFT_MISO 305 #define TFT_MISO -1 306 #endif 307 308 #ifndef TFT_MOSI 309 #define TFT_MOSI 23 310 #endif 311 #if (TFT_MOSI == -1) 312 #undef TFT_MOSI 313 #define TFT_MOSI 23 314 #endif 315 316 #ifndef TFT_SCLK 317 #define TFT_SCLK 18 318 #endif 319 #if (TFT_SCLK == -1) 320 #undef TFT_SCLK 321 #define TFT_SCLK 18 322 #endif 323 324 #if defined(CONFIG_IDF_TARGET_ESP32C3) || defined(CONFIG_IDF_TARGET_ESP32S2) 325 #if (TFT_MISO == -1) 326 #undef TFT_MISO 327 #define TFT_MISO TFT_MOSI 328 #endif 329 #endif 330 331 #endif 332 333 #endif 334 335 //////////////////////////////////////////////////////////////////////////////////////// 336 // Define the parallel bus interface chip pin drive code 337 //////////////////////////////////////////////////////////////////////////////////////// 338 #if defined (TFT_PARALLEL_8_BIT) 339 340 // Create a bit set lookup table for data bus - wastes 1kbyte of RAM but speeds things up dramatically 341 // can then use e.g. GPIO.out_w1ts = set_mask(0xFF); to set data bus to 0xFF 342 #define PARALLEL_INIT_TFT_DATA_BUS \ 343 for (int32_t c = 0; c<256; c++) \ 344 { \ 345 xset_mask[c] = 0; \ 346 if ( c & 0x01 ) xset_mask[c] |= (1 << TFT_D0); \ 347 if ( c & 0x02 ) xset_mask[c] |= (1 << TFT_D1); \ 348 if ( c & 0x04 ) xset_mask[c] |= (1 << TFT_D2); \ 349 if ( c & 0x08 ) xset_mask[c] |= (1 << TFT_D3); \ 350 if ( c & 0x10 ) xset_mask[c] |= (1 << TFT_D4); \ 351 if ( c & 0x20 ) xset_mask[c] |= (1 << TFT_D5); \ 352 if ( c & 0x40 ) xset_mask[c] |= (1 << TFT_D6); \ 353 if ( c & 0x80 ) xset_mask[c] |= (1 << TFT_D7); \ 354 } \ 355 356 // Mask for the 8 data bits to set pin directions 357 #define GPIO_DIR_MASK ((1 << TFT_D0) | (1 << TFT_D1) | (1 << TFT_D2) | (1 << TFT_D3) | (1 << TFT_D4) | (1 << TFT_D5) | (1 << TFT_D6) | (1 << TFT_D7)) 358 359 #if (TFT_WR >= 32) 360 // Data bits and the write line are cleared sequentially 361 #define GPIO_OUT_CLR_MASK (GPIO_DIR_MASK); WR_L 362 #elif (TFT_WR >= 0) 363 // Data bits and the write line are cleared to 0 in one step (1.25x faster) 364 #define GPIO_OUT_CLR_MASK (GPIO_DIR_MASK | (1 << TFT_WR)) 365 #else 366 #define GPIO_OUT_CLR_MASK 367 #endif 368 369 // A lookup table is used to set the different bit patterns, this uses 1kByte of RAM 370 #define set_mask(C) xset_mask[C] // 63fps Sprite rendering test 33% faster, graphicstest only 1.8% faster than shifting in real time 371 372 // Real-time shifting alternative to above to save 1KByte RAM, 47 fps Sprite rendering test 373 /*#define set_mask(C) (((C)&0x80)>>7)<<TFT_D7 | (((C)&0x40)>>6)<<TFT_D6 | (((C)&0x20)>>5)<<TFT_D5 | (((C)&0x10)>>4)<<TFT_D4 | \ 374 (((C)&0x08)>>3)<<TFT_D3 | (((C)&0x04)>>2)<<TFT_D2 | (((C)&0x02)>>1)<<TFT_D1 | (((C)&0x01)>>0)<<TFT_D0 375 //*/ 376 377 // Write 8 bits to TFT 378 #define tft_Write_8(C) GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t)(C)); WR_H 379 380 #if defined (SSD1963_DRIVER) 381 382 // Write 18 bit color to TFT 383 #define tft_Write_16(C) GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) (((C) & 0xF800)>> 8)); WR_H; \ 384 GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) (((C) & 0x07E0)>> 3)); WR_H; \ 385 GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) (((C) & 0x001F)<< 3)); WR_H 386 387 // 18 bit color write with swapped bytes 388 #define tft_Write_16S(C) Cswap = ((C) >>8 | (C) << 8); tft_Write_16(Cswap) 389 390 #else 391 392 #ifdef PSEUDO_16_BIT 393 // One write strobe for both bytes 394 #define tft_Write_16(C) GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) ((C) >> 0)); WR_H 395 #define tft_Write_16S(C) GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) ((C) >> 8)); WR_H 396 #else 397 // Write 16 bits to TFT 398 #define tft_Write_16(C) GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) ((C) >> 8)); WR_H; \ 399 GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) ((C) >> 0)); WR_H 400 401 // 16 bit write with swapped bytes 402 #define tft_Write_16S(C) GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) ((C) >> 0)); WR_H; \ 403 GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) ((C) >> 8)); WR_H 404 #endif 405 406 #endif 407 408 // Write 32 bits to TFT 409 #define tft_Write_32(C) GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) ((C) >> 24)); WR_H; \ 410 GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) ((C) >> 16)); WR_H; \ 411 GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) ((C) >> 8)); WR_H; \ 412 GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) ((C) >> 0)); WR_H 413 414 // Write two concatenated 16 bit values to TFT 415 #define tft_Write_32C(C,D) GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) ((C) >> 8)); WR_H; \ 416 GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) ((C) >> 0)); WR_H; \ 417 GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) ((D) >> 8)); WR_H; \ 418 GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) ((D) >> 0)); WR_H 419 420 // Write 16 bit value twice to TFT - used by drawPixel() 421 #define tft_Write_32D(C) GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) ((C) >> 8)); WR_H; \ 422 GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) ((C) >> 0)); WR_H; \ 423 GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) ((C) >> 8)); WR_H; \ 424 GPIO.out_w1tc = GPIO_OUT_CLR_MASK; GPIO.out_w1ts = set_mask((uint8_t) ((C) >> 0)); WR_H 425 426 // Read pin 427 #ifdef TFT_RD 428 #if (TFT_RD >= 32) 429 #define RD_L GPIO.out1_w1tc.val = (1 << (TFT_RD - 32)) 430 #define RD_H GPIO.out1_w1ts.val = (1 << (TFT_RD - 32)) 431 #elif (TFT_RD >= 0) 432 #define RD_L GPIO.out_w1tc = (1 << TFT_RD) 433 //#define RD_L digitalWrite(TFT_WR, LOW) 434 #define RD_H GPIO.out_w1ts = (1 << TFT_RD) 435 //#define RD_H digitalWrite(TFT_WR, HIGH) 436 #else 437 #define RD_L 438 #define RD_H 439 #endif 440 #else 441 #define TFT_RD -1 442 #define RD_L 443 #define RD_H 444 #endif 445 446 //////////////////////////////////////////////////////////////////////////////////////// 447 // Macros to write commands/pixel colour data to a SPI ILI948x TFT 448 //////////////////////////////////////////////////////////////////////////////////////// 449 #elif defined (SPI_18BIT_DRIVER) // SPI 18 bit colour 450 451 // Write 8 bits to TFT 452 #define tft_Write_8(C) spi.transfer(C) 453 454 // Convert 16 bit colour to 18 bit and write in 3 bytes 455 #define tft_Write_16(C) spi.transfer(((C) & 0xF800)>>8); \ 456 spi.transfer(((C) & 0x07E0)>>3); \ 457 spi.transfer(((C) & 0x001F)<<3) 458 459 // Future option for transfer without wait 460 #define tft_Write_16N(C) tft_Write_16(C) 461 462 // Convert swapped byte 16 bit colour to 18 bit and write in 3 bytes 463 #define tft_Write_16S(C) spi.transfer((C) & 0xF8); \ 464 spi.transfer(((C) & 0xE000)>>11 | ((C) & 0x07)<<5); \ 465 spi.transfer(((C) & 0x1F00)>>5) 466 467 // Write 32 bits to TFT 468 #define tft_Write_32(C) spi.write32(C) 469 470 // Write two concatenated 16 bit values to TFT 471 #define tft_Write_32C(C,D) spi.write32((C)<<16 | (D)) 472 473 // Write 16 bit value twice to TFT 474 #define tft_Write_32D(C) spi.write32((C)<<16 | (C)) 475 476 //////////////////////////////////////////////////////////////////////////////////////// 477 // Macros to write commands/pixel colour data to an Raspberry Pi TFT 478 //////////////////////////////////////////////////////////////////////////////////////// 479 #elif defined (RPI_DISPLAY_TYPE) 480 481 // ESP32 low level SPI writes for 8, 16 and 32 bit values 482 // to avoid the function call overhead 483 #define TFT_WRITE_BITS(D, B) \ 484 WRITE_PERI_REG(SPI_MOSI_DLEN_REG(SPI_PORT), B-1); \ 485 WRITE_PERI_REG(SPI_W0_REG(SPI_PORT), D); \ 486 SET_PERI_REG_MASK(SPI_CMD_REG(SPI_PORT), SPI_USR); \ 487 while (READ_PERI_REG(SPI_CMD_REG(SPI_PORT))&SPI_USR); 488 489 // Write 8 bits 490 #define tft_Write_8(C) TFT_WRITE_BITS((C)<<8, 16) 491 492 // Write 16 bits with corrected endianness for 16 bit colours 493 #define tft_Write_16(C) TFT_WRITE_BITS((C)<<8 | (C)>>8, 16) 494 495 // Future option for transfer without wait 496 #define tft_Write_16N(C) tft_Write_16(C) 497 498 // Write 16 bits 499 #define tft_Write_16S(C) TFT_WRITE_BITS(C, 16) 500 501 // Write 32 bits 502 #define tft_Write_32(C) TFT_WRITE_BITS(C, 32) 503 504 // Write two address coordinates 505 #define tft_Write_32C(C,D) TFT_WRITE_BITS((C)<<24 | (C), 32); \ 506 TFT_WRITE_BITS((D)<<24 | (D), 32) 507 508 // Write same value twice 509 #define tft_Write_32D(C) tft_Write_32C(C,C) 510 511 //////////////////////////////////////////////////////////////////////////////////////// 512 // Macros for all other SPI displays 513 //////////////////////////////////////////////////////////////////////////////////////// 514 #else 515 /* Old macros 516 // ESP32 low level SPI writes for 8, 16 and 32 bit values 517 // to avoid the function call overhead 518 #define TFT_WRITE_BITS(D, B) \ 519 WRITE_PERI_REG(SPI_MOSI_DLEN_REG(SPI_PORT), B-1); \ 520 WRITE_PERI_REG(SPI_W0_REG(SPI_PORT), D); \ 521 SET_PERI_REG_MASK(SPI_CMD_REG(SPI_PORT), SPI_USR); \ 522 while (READ_PERI_REG(SPI_CMD_REG(SPI_PORT))&SPI_USR); 523 524 // Write 8 bits 525 #define tft_Write_8(C) TFT_WRITE_BITS(C, 8) 526 527 // Write 16 bits with corrected endianness for 16 bit colours 528 #define tft_Write_16(C) TFT_WRITE_BITS((C)<<8 | (C)>>8, 16) 529 530 // Write 16 bits 531 #define tft_Write_16S(C) TFT_WRITE_BITS(C, 16) 532 533 // Write 32 bits 534 #define tft_Write_32(C) TFT_WRITE_BITS(C, 32) 535 536 // Write two address coordinates 537 #define tft_Write_32C(C,D) TFT_WRITE_BITS((uint16_t)((D)<<8 | (D)>>8)<<16 | (uint16_t)((C)<<8 | (C)>>8), 32) 538 539 // Write same value twice 540 #define tft_Write_32D(C) TFT_WRITE_BITS((uint16_t)((C)<<8 | (C)>>8)<<16 | (uint16_t)((C)<<8 | (C)>>8), 32) 541 //*/ 542 //* Replacement slimmer macros 543 #define TFT_WRITE_BITS(D, B) *_spi_mosi_dlen = B-1; \ 544 *_spi_w = D; \ 545 *_spi_cmd = SPI_USR; \ 546 while (*_spi_cmd & SPI_USR); 547 548 // Write 8 bits 549 #define tft_Write_8(C) TFT_WRITE_BITS(C, 8) 550 551 // Write 16 bits with corrected endianness for 16 bit colours 552 #define tft_Write_16(C) TFT_WRITE_BITS((C)<<8 | (C)>>8, 16) 553 554 // Future option for transfer without wait 555 #define tft_Write_16N(C) *_spi_mosi_dlen = 16-1; \ 556 *_spi_w = ((C)<<8 | (C)>>8); \ 557 *_spi_cmd = SPI_USR; 558 559 // Write 16 bits 560 #define tft_Write_16S(C) TFT_WRITE_BITS(C, 16) 561 562 // Write 32 bits 563 #define tft_Write_32(C) TFT_WRITE_BITS(C, 32) 564 565 // Write two address coordinates 566 #define tft_Write_32C(C,D) TFT_WRITE_BITS((uint16_t)((D)<<8 | (D)>>8)<<16 | (uint16_t)((C)<<8 | (C)>>8), 32) 567 568 // Write same value twice 569 #define tft_Write_32D(C) TFT_WRITE_BITS((uint16_t)((C)<<8 | (C)>>8)<<16 | (uint16_t)((C)<<8 | (C)>>8), 32) 570 571 //*/ 572 #endif 573 574 #ifndef tft_Write_16N 575 #define tft_Write_16N tft_Write_16 576 #endif 577 578 //////////////////////////////////////////////////////////////////////////////////////// 579 // Macros to read from display using SPI or software SPI 580 //////////////////////////////////////////////////////////////////////////////////////// 581 #if !defined (TFT_PARALLEL_8_BIT) 582 // Read from display using SPI or software SPI 583 // Use a SPI read transfer 584 #define tft_Read_8() spi.transfer(0) 585 #endif 586 587 // Concatenate a byte sequence A,B,C,D to CDAB, P is a uint8_t pointer 588 #define DAT8TO32(P) ( (uint32_t)P[0]<<8 | P[1] | P[2]<<24 | P[3]<<16 ) 589 590 #endif // Header end