Skip to content
Snippets Groups Projects
Commit cf5ae77a authored by Mateusz Zalega's avatar Mateusz Zalega Committed by q3k
Browse files

LCD: implemented double buffering and asynchronous updates

parent 9cd56629
No related branches found
No related tags found
No related merge requests found
......@@ -39,10 +39,11 @@
static spi_req_t req = {.rx_data = NULL, .bits=8, .width = SPI17Y_WIDTH_1, .ssel = 0, .deass = 1, .ssel_pol = SPI17Y_POL_LOW, .tx_num = 0, .rx_num = 0};
/********************************************************************************/
void lcd_write(uint8_t *data, int size)
void lcd_write(uint8_t *data, int size, lcd_write_cb_t wr_callback)
{
req.tx_data = data;
req.len = size;
SPI_MasterTrans(SPI, &req);
req.callback = wr_callback;
SPI_MasterTransAsync(SPI, &req);
}
......@@ -43,6 +43,8 @@
#define UWORD uint16_t
#define UDOUBLE uint32_t
typedef spi_callback_fn lcd_write_cb_t;
/**
* GPIO config
**/
......@@ -57,9 +59,9 @@ extern const gpio_cfg_t DEV_DC_PIN;
/**
* SPI
**/
void lcd_write(uint8_t* data, int size);
void lcd_write(uint8_t* data, int size, lcd_write_cb_t wr_callback);
void display_set_reset_pin(uint8_t state);
#define DEV_SPI_WRITE(_dat) lcd_write(&_dat, 1)
#define DEV_SPI_WRITE(_dat) lcd_write(&_dat, 1, NULL)
#define DEV_RESET_LOW() display_set_reset_pin(0)
#define DEV_RESET_HIGH() display_set_reset_pin(1)
/**
......
......@@ -28,7 +28,27 @@
#
******************************************************************************/
#include "LCD_Driver.h"
static uint8_t screen[LCD_HEIGHT][LCD_WIDTH][2];
typedef union {
uint8_t fb[LCD_HEIGHT][LCD_WIDTH][2];
uint8_t raw[LCD_HEIGHT * LCD_WIDTH * 2];
} frame_t;
static frame_t frames[2];
static uint8_t active_frame;
static uint8_t update_in_progress;
#define FRAME_SIZE sizeof(frames[0])
static inline frame_t *frame(void)
{
return &frames[active_frame];
}
static void update_cb(void *spi_req, int error_code)
{
update_in_progress = 0;
}
/*******************************************************************************
function:
......@@ -197,7 +217,7 @@ parameter :
Xend : End UWORD coordinates
Yend : End UWORD coordinatesen
******************************************************************************/
void LCD_SetCursor(UWORD Xstart, UWORD Ystart, UWORD Xend, UWORD Yend)
static void LCD_SetCursor(UWORD Xstart, UWORD Ystart, UWORD Xend, UWORD Yend)
{
Xstart = Xstart + 1;
Xend = Xend + 1;
......@@ -289,8 +309,8 @@ void LCD_SetUWORD(UWORD x, UWORD y, UWORD Color)
void LCD_SetUWORD(UWORD x, UWORD y, UWORD Color)
{
screen[y][x][0] = (Color >> 8);
screen[y][x][1] = (Color & 0xFF);
frame()->fb[y][x][0] = (Color >> 8);
frame()->fb[y][x][1] = (Color & 0xFF);
}
void LCD_Clear(UWORD Color)
......@@ -303,14 +323,21 @@ void LCD_Clear(UWORD Color)
}
}
void LCD_Set(uint8_t *data, int len)
static void LCD_Set(uint8_t *data, int len)
{
LCD_SetCursor(0, 0, 160 - 1, 80 - 1);
DEV_Digital_Write(DEV_DC_PIN, 1);
lcd_write(data, len);
update_in_progress = 1;
lcd_write(data, len, update_cb);
}
void LCD_Update(void)
int LCD_Update(void)
{
LCD_Set((uint8_t *)screen, sizeof(screen));
if (update_in_progress)
return 1;
LCD_Set(frame()->raw, FRAME_SIZE);
active_frame = !active_frame;
return 0;
}
......@@ -40,7 +40,6 @@ void LCD_WriteData_Byte(UBYTE da);
void LCD_WriteData_Word(UWORD da);
void LCD_WriteReg(UBYTE da);
void LCD_SetCursor(UWORD x1, UWORD y1, UWORD x2,UWORD y2);
void LCD_SetUWORD(UWORD x, UWORD y, UWORD Color);
void LCD_Init(void);
......@@ -48,7 +47,10 @@ void LCD_SetBacklight(UWORD Value);
void LCD_Clear(UWORD Color);
void LCD_ClearWindow(UWORD Xstart, UWORD Ystart, UWORD Xend, UWORD Yend, UWORD UWORD);
void LCD_Set(uint8_t *data, int len);
void LCD_Update(void);
/*
* return value: 0 - asynchronous update was scheduled
* 1 - an update was already in progress
*/
int LCD_Update(void);
#endif
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment