Been looking into that, thanks David.
I'm searching for the fastest way to move an image with BLACK as the transparent color.
The code below moves vertically an image (lunar lander) stored in PROGMEM, while writing only non-BLACK pixels. bGround PROGMEM fills in the background behind the lander image's BLACK pixels.
I'm getting 11 fps (90ms) using a Due and Mcufriend ILI9486 Uno shield.
Note: Rename Moon320x240.raw.ino to Moon320x240.raw and drop it in the root dir on sd card. Don't need Moonscape320x240.h unless you modify code to use it in PROGMEM instead of raw image on sd card.
#include "Adafruit_GFX.h" // Core graphics library
#include <MCUFRIEND_kbv.h>
MCUFRIEND_kbv tft;
#include <SdFat.h>
SdFat SD;
SdFile file;
#define sd_chipSelect SS // Card select for shield use
#define BLACK 0x0000
#define BLUE 0x001F
#define RED 0xF800
#define GREEN 0x07E0
#define CYAN 0x07FF
#define MAGENTA 0xF81F
#define YELLOW 0xFFE0
#define WHITE 0xFFFF
#define GREY 0x7BEF
#define Cyan 0x07FF
#define DarkCyan 0x03EF
#include "LunarLander92x68.h"
#include "Moonscape320x240.h"
uint16_t bGround[22816];
int yy = 200; // Lunar Lander starting y pos
int moonY = 239; // Moonscape starting y pos
int16_t countHt=0;
void setup() {
Serial.begin(115200);
tft.reset();
Serial.println(tft.readID(), HEX);
tft.begin(tft.readID());
//tft.begin(0x9486);
//tft.invertDisplay(true);
tft.fillScreen(0);
tft.setRotation(4);
SD.begin(sd_chipSelect);
SD.chdir("/");
tft.setRotation(4);
tft.fillScreen(BLACK);
tft.setTextColor(WHITE, BLACK);
tft.setTextSize(2);
int x=160,wid=92,ht=68, yht=1;
drawRAW("Moon320x240.raw",0, 240, 320, 240);
tft.readGRAM(x, yy, bGround, wid, 180+68); //x = 160, yy = 200, wid = 92
}
void loop() {
uint32_t startTime = millis();
int x=160,wid=92,ht=68, yht=1;
countHt = 1;
for (int y = yy; y <= 380; y+=yht) {
uint32_t startTime = millis();
drawRGBraw (x, y, LunarLander, wid, ht);
countHt++;
tft.setCursor(235, 5);
int FPS = 1000 / (millis() - startTime);
tft.print (FPS);
tft.print (" FPS");
//screenServer();
}
delay(2000);
tft.setAddrWindow(x, yy, 252, 448); //x = 160, yy = 200
tft.pushColors(bGround, sizeof(bGround)/2, 1);
}
void drawRGBraw(int16_t x, int16_t y, const uint16_t lander[], int16_t w, int16_t h) {
for (int16_t j = 0; j < h; j++, y++) { // vert pos counter
for (int16_t i = 0; i < w; i++) { // horz pos counter
uint16_t landerPix;
landerPix = pgm_read_word(&lander[j * w + i]); // get next pixel from lunar lander PROGMEM
if (landerPix != BLACK) // Make BLACK transparent
tft.writePixel(x + i, y, landerPix);
else {
uint16_t bGroundPix = pgm_read_word(&bGround[(countHt+j) * w + i]);
tft.writePixel(x + i, y, bGroundPix); // if landerPix is black, fill with backround
}
}
}
}
Moonscape320x240.h (531.6 KB)
screenServer.ino (4.3 KB)
LunarLander92x68.h (49.4 KB)
DrawRaw565.ino (1.1 KB)
Moon320x240.raw.ino (150 KB)
TFT_Due_MCUfriend_UnoShield_LunarLander3.ino (3.8 KB)