Since i have been getting the ili9341 display ready for fast 32x32 (and 64x64, 128x128) subsampling of amg8833 sensor the ili9341 display has 4 times as many pixels as the st7735 display i have working at fast speeds. to increase performance i am doing tricks that cut down display writes to about half, and the rest is thru driver optimizations.
I have found out that the driver for set window always sends 4 byte commands for x, and 4 byte commands for y no matter what the display position is, yet most of the time only one or the other is needed.
here is the setAddrWindow command driver as it is in ili9341 driver :
void Adafruit_ILI9341::setAddrWindow(uint16_t x, uint16_t y, uint16_t w, uint16_t h) {
uint32_t xa = ((uint32_t)x << 16) | (x+w-1);
uint32_t ya = ((uint32_t)y << 16) | (y+h-1);
writeCommand(ILI9341_CASET); // Column addr set
SPI_WRITE32(xa);
writeCommand(ILI9341_PASET); // Row addr set
SPI_WRITE32(ya);
writeCommand(ILI9341_RAMWR); // write to RAM
}
here is my optimization. it reduces command overhead by 33%. still you will need to send either x, or y and at least set ram buffer command on each screen location update. my goal is to not use screen location updates but they are needed at least for every square block write to display (64 times) or when only writing half the display one time per line call so we can skip a line, so 64x15 (64 blocks. a block on this display is 30x32 pixels) or 960 times per frame. the time savings is significant enough to raise frame rates about 20% in itself when doing half fill mode as location window changes every other line for fills within a fill square of multiple colors.
keep in mind the caching of values and comparing. if no change we don't write both x and y we only update one of them.
long xaCache ; //two ram values that use 4 bytes each are needed to make this work.
long yaCache; //place values at top of page where the code is, in my case it is adafruit_ili9341.cpp
void Adafruit_ILI9341::setAddrWindow(uint16_t x, uint16_t y, uint16_t w, uint16_t h) {
uint32_t xa = ((uint32_t)x << 16) | (x+w-1);
uint32_t ya = ((uint32_t)y << 16) | (y+h-1);
if (xaCache != xa){
writeCommand(ILI9341_CASET); // Column addr set
SPI_WRITE32(xa);xaCache = xa;
}
if (yaCache != ya){
writeCommand(ILI9341_PASET); // Row addr set
SPI_WRITE32(ya);yaCache = ya;
}
writeCommand(ILI9341_RAMWR); // write to RAM
}
Discussions
Become a Hackaday.io Member
Create an account to leave a comment. Already have an account? Log In.