[STM32 learning record 4] - 1.44-inch TFT LCD displays characters, Chinese characters and pictures

Keywords: Programming

Author: AXYZdong
Automation Engineering Male
A little thought, a little thought, a little rationality

Summary

MCU: STM32F407VET6 minimum system board of a treasure, Click here for details.
External resources: TFT LCD screen of a treasure (pictures will be attached below)
Click here to download the complete project
There are surprises at the end of the article. I hope we can keep reading

4.1 hardware design

Pin Pin description
VCC Positive power supply
GND Negative power supply
NC no connect, no wiring required
LED Backlight control signal
CLK(SCL) SPI bus clock pin
SDI(SDA) SPI bus data pin
RS Register / data selection control pin
RST Reset control pin
CS Chip selection control pin

Here's a little question: why two GND and NC? Don't know what the manufacturer thinks? You can trust me if you know me.

Note that the NC pin does not need to be wired.
LED: backlight control signal, if no control is needed, connect power + 3.3V
Key words: SPI bus driver

4.2 software design

4.2.1 key points of programming

1. Initialize the GPIO port to simulate SPI. The GPIO port set by each person is different, and the connection between the development board and TFT is also different. Then set LCD initialization.

2. TFT driver, the driver here can refer to other people's writing, and then modify or supplement by yourself. Drivers include: write data to TFT, set TFT display area, set TFT color at a certain point, etc., which are explained in the code.

3. Take the mold, including the text mold and the picture mold. Take the mold according to your own needs. Those who need the software can send it to me.
PS: in fact, these steps are similar to the OLED in the previous article, just for a moment

4.2.2 code description

1. Macro definition LCD? Driver. H

#define RED  	  0xf800
#define GREEN	  0x07e0
#define BLUE 	  0x001f
#define WHITE	  0xffff
#define BLACK	  0x0000
#define YELLOW  0xFFE0
#define GRAY0   0xEF7D   	    //Grey 0 3165 00110 001011 00101
#define GRAY1   0x8410      	//Grey 1 00000 00000000000
#define GRAY2   0x4208      	//Grey 21111111111011111

#define LCD_CTRL   	  	GPIOB		//Define TFT data port
#define LCD_LED        	GPIO_Pin_9  //MCU_PB9--->>TFT --BL
#define LCD_SCL        	GPIO_Pin_10	//PB13--->>TFT --SCL/SCK
#define LCD_SDA        	GPIO_Pin_12	//PB15 MOSI--->>TFT --SDA/DIN
#define LCD_RS         	GPIO_Pin_11	//PB11--->>TFT --RS/DC
#define LCD_RST     	  GPIO_Pin_14	//PB10--->>TFT --RST
#define LCD_CS        	GPIO_Pin_13  //MCU_PB11--->>TFT --CS/CE

//#define LCD_CS_SET(x) LCD_CTRL->ODR=(LCD_CTRL->ODR&~LCD_CS)|(x ? LCD_CS:0)
//Macro definition of operation statement of LCD control port 1

#define	LCD_CS_SET  	LCD_CTRL->BSRRL=LCD_CS    
#define	LCD_RS_SET  	LCD_CTRL->BSRRL=LCD_RS    
#define	LCD_SDA_SET  	LCD_CTRL->BSRRL=LCD_SDA    
#define	LCD_SCL_SET  	LCD_CTRL->BSRRL=LCD_SCL    
#define	LCD_RST_SET  	LCD_CTRL->BSRRL=LCD_RST    
#define	LCD_LED_SET  	LCD_CTRL->BSRRL=LCD_LED   

//Macro definition of operation statement of LCD control port 0
#define	LCD_CS_CLR  	LCD_CTRL->BSRRH=LCD_CS    
#define	LCD_RS_CLR  	LCD_CTRL->BSRRH=LCD_RS    
#define	LCD_SDA_CLR  	LCD_CTRL->BSRRH=LCD_SDA    
#define	LCD_SCL_CLR  	LCD_CTRL->BSRRH=LCD_SCL    
#define	LCD_RST_CLR  	LCD_CTRL->BSRRH=LCD_RST    
#define	LCD_LED_CLR  	LCD_CTRL->BSRRH=LCD_LED 
#define LCD_DATAOUT(x) LCD_DATA->ODR=x; //data output
#define LCD_DATAIN     LCD_DATA->IDR;   //data input
#define LCD_WR_DATA(data){\

LCD_RS_SET;\
LCD_CS_CLR;\
LCD_DATAOUT(data);\
LCD_WR_CLR;\
LCD_WR_SET;\
LCD_CS_SET;\
} 

void LCD_GPIO_Init(void);
void Lcd_WriteIndex(u8 Index);
void Lcd_WriteData(u8 Data);
void Lcd_WriteReg(u8 Index,u8 Data);
u16 Lcd_ReadReg(u8 LCD_Reg);
void Lcd_Reset(void);
void Lcd_Init(void);
void Lcd_Clear(u16 Color);
void Lcd_SetXY(u16 x,u16 y);
void Gui_DrawPoint(u16 x,u16 y,u16 Data);
unsigned int Lcd_ReadPoint(u16 x,u16 y);
void Lcd_SetRegion(u16 x_start,u16 y_start,u16 x_end,u16 y_end);
void LCD_WriteData_16Bit(u16 Data);

2. TFT driver file LCD? Driver. C

#include "stm32f4xx.h"
#include "Lcd_Driver.h"
#include "LCD_Config.h"
#include "delay.h"

//This program uses an analog SPI interface driver
//The IO configuration of the interface can be changed freely, and the LCD drive display can be completed by using any 4 IO at least

//The interface is defined in LCD? Driver.h Internal definition, please modify according to the wiring and modify the corresponding IO InitializationLCD_GPIO_Init()
#define LCD_CTRL   	  	GPIOB		//Define TFT data port
#define LCD_LED        	GPIO_Pin_9  //PB9--->>TFT --BL
#define LCD_RS         	GPIO_Pin_10	//PB11--->>TFT --RS/DC
#define LCD_CS        	GPIO_Pin_11  //PB11--->>TFT --CS/CE
#define LCD_RST     		GPIO_Pin_12	//PB10--->>TFT --RST
#define LCD_SCL        	GPIO_Pin_13	//PB13--->>TFT --SCL/SCK
#define LCD_SDA        	GPIO_Pin_15	//PB15 MOSI--->>TFT --SDA/DIN
*******************************************************************************/

//LCD IO initialization configuration
void LCD_GPIO_Init(void)
{
	GPIO_InitTypeDef  GPIO_InitStructure;      
	RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOB ,ENABLE);	
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9| GPIO_Pin_10| GPIO_Pin_11| GPIO_Pin_12 | GPIO_Pin_13 | GPIO_Pin_14| GPIO_Pin_15;
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;
	GPIO_Init(GPIOB, &GPIO_InitStructure);
      
}
//Transfer an 8-bit data to SPI bus
void  SPI_WriteData(u8 Data)
{
	unsigned char i=0;
	for(i=8;i>0;i--)
	{
		if(Data&0x80)	
	  LCD_SDA_SET; //output data
      else LCD_SDA_CLR;
	   
      LCD_SCL_CLR;       
      LCD_SCL_SET;
      Data<<=1; 
	}
}
//Write an 8-bit instruction to the LCD
void Lcd_WriteIndex(u8 Index)
{
   //SPI write command sequence start
   LCD_CS_CLR;
   LCD_RS_CLR;
	 SPI_WriteData(Index);
   LCD_CS_SET;
}

//Write an 8-bit data to the LCD
void Lcd_WriteData(u8 Data)
{
   LCD_CS_CLR;
   LCD_RS_SET;
   SPI_WriteData(Data);
   LCD_CS_SET; 
}
//Write a 16 bit data to the LCD
void LCD_WriteData_16Bit(u16 Data)
{
   LCD_CS_CLR;
   LCD_RS_SET;
	 SPI_WriteData(Data>>8); 	  //Write high 8-bit data
	 SPI_WriteData(Data); 			//Write low 8-bit data
   LCD_CS_SET; 
}

void Lcd_WriteReg(u8 Index,u8 Data)
{
	Lcd_WriteIndex(Index);
  Lcd_WriteData(Data);
}

void Lcd_Reset(void)
{
	LCD_RST_CLR;
	delay_ms(100);
	LCD_RST_SET;
	delay_ms(50);
}

//LCD Init For 1.44Inch LCD Panel with ST7735R.
void Lcd_Init(void)
{	
	LCD_GPIO_Init();
	Lcd_Reset(); //Reset before LCD Init.

	//LCD Init For 1.44Inch LCD Panel with ST7735R.
	Lcd_WriteIndex(0x11);//Sleep exit 
	delay_ms (120);
		
	//ST7735R Frame Rate
	Lcd_WriteIndex(0xB1); 
	Lcd_WriteData(0x01); 
	Lcd_WriteData(0x2C); 
	Lcd_WriteData(0x2D); 

	Lcd_WriteIndex(0xB2); 
	Lcd_WriteData(0x01); 
	Lcd_WriteData(0x2C); 
	Lcd_WriteData(0x2D); 

	Lcd_WriteIndex(0xB3); 
	Lcd_WriteData(0x01); 
	Lcd_WriteData(0x2C); 
	Lcd_WriteData(0x2D); 
	Lcd_WriteData(0x01); 
	Lcd_WriteData(0x2C); 
	Lcd_WriteData(0x2D); 
	
	Lcd_WriteIndex(0xB4); //Column inversion 
	Lcd_WriteData(0x07); 
	
	//ST7735R Power Sequence
	Lcd_WriteIndex(0xC0); 
	Lcd_WriteData(0xA2); 
	Lcd_WriteData(0x02); 
	Lcd_WriteData(0x84); 
	Lcd_WriteIndex(0xC1); 
	Lcd_WriteData(0xC5); 

	Lcd_WriteIndex(0xC2); 
	Lcd_WriteData(0x0A); 
	Lcd_WriteData(0x00); 

	Lcd_WriteIndex(0xC3); 
	Lcd_WriteData(0x8A); 
	Lcd_WriteData(0x2A); 
	Lcd_WriteIndex(0xC4); 
	Lcd_WriteData(0x8A); 
	Lcd_WriteData(0xEE); 
	
	Lcd_WriteIndex(0xC5); //VCOM 
	Lcd_WriteData(0x0E); 
	
	Lcd_WriteIndex(0x36); //MX, MY, RGB mode 
	Lcd_WriteData(0xC8); 
	
	//ST7735R Gamma Sequence
	Lcd_WriteIndex(0xe0); 
	Lcd_WriteData(0x0f); 
	Lcd_WriteData(0x1a); 
	Lcd_WriteData(0x0f); 
	Lcd_WriteData(0x18); 
	Lcd_WriteData(0x2f); 
	Lcd_WriteData(0x28); 
	Lcd_WriteData(0x20); 
	Lcd_WriteData(0x22); 
	Lcd_WriteData(0x1f); 
	Lcd_WriteData(0x1b); 
	Lcd_WriteData(0x23); 
	Lcd_WriteData(0x37); 
	Lcd_WriteData(0x00); 	
	Lcd_WriteData(0x07); 
	Lcd_WriteData(0x02); 
	Lcd_WriteData(0x10); 

	Lcd_WriteIndex(0xe1); 
	Lcd_WriteData(0x0f); 
	Lcd_WriteData(0x1b); 
	Lcd_WriteData(0x0f); 
	Lcd_WriteData(0x17); 
	Lcd_WriteData(0x33); 
	Lcd_WriteData(0x2c); 
	Lcd_WriteData(0x29); 
	Lcd_WriteData(0x2e); 
	Lcd_WriteData(0x30); 
	Lcd_WriteData(0x30); 
	Lcd_WriteData(0x39); 
	Lcd_WriteData(0x3f); 
	Lcd_WriteData(0x00); 
	Lcd_WriteData(0x07); 
	Lcd_WriteData(0x03); 
	Lcd_WriteData(0x10);  
	
	Lcd_WriteIndex(0x2a);
	Lcd_WriteData(0x00);
	Lcd_WriteData(0x00);
	Lcd_WriteData(0x00);
	Lcd_WriteData(0x7f);

	Lcd_WriteIndex(0x2b);
	Lcd_WriteData(0x00);
	Lcd_WriteData(0x00);
	Lcd_WriteData(0x00);
	Lcd_WriteData(0x9f);
	
	Lcd_WriteIndex(0xF0); //Enable test command  
	Lcd_WriteData(0x01); 
	Lcd_WriteIndex(0xF6); //Disable ram power save mode 
	Lcd_WriteData(0x00); 
	
	Lcd_WriteIndex(0x3A); //65k mode 
	Lcd_WriteData(0x05); 
	
	
	Lcd_WriteIndex(0x29);//Display on	 
}


/*************************************************
Function name: LCD set region
 Function: set lcd display area, write point data in this area to wrap automatically
 Entry parameters: xy start and end
 Return value: None
*************************************************/
void Lcd_SetRegion(u16 x_start,u16 y_start,u16 x_end,u16 y_end)
{		
	Lcd_WriteIndex(0x2a);
	Lcd_WriteData(0x00);
	Lcd_WriteData(x_start+2);
	Lcd_WriteData(0x00);
	Lcd_WriteData(x_end+2);

	Lcd_WriteIndex(0x2b);
	Lcd_WriteData(0x00);
	Lcd_WriteData(y_start+3);
	Lcd_WriteData(0x00);
	Lcd_WriteData(y_end+3);
	
	Lcd_WriteIndex(0x2c);

}

/*************************************************
Function name: LCD set XY
 Function: set lcd display starting point
 Entry parameter: xy coordinate
 Return value: None
*************************************************/
void Lcd_SetXY(u16 x,u16 y)
{
  	Lcd_SetRegion(x,y,x,y);
}

	
/*************************************************
Function name: LCD drawpoint
 Function: draw a point
 Entry parameter: None
 Return value: None
*************************************************/
void Gui_DrawPoint(u16 x,u16 y,u16 Data)
{
	Lcd_SetRegion(x,y,x+1,y+1);
	LCD_WriteData_16Bit(Data);

}    

/*****************************************
 Function function: read the color of a point in TFT                          
 Exit parameter: color dot color value                                 
******************************************/
unsigned int Lcd_ReadPoint(u16 x,u16 y)
{
  unsigned int Data;
  Lcd_SetXY(x,y);

  //Lcd_ReadData(); / / discard useless bytes
  //Data=Lcd_ReadData();
  Lcd_WriteData(Data);
  return Data;
}
/*************************************************
Function name: LCD? Clear
 Function: full screen clearing function
 Entry parameters: fill COLOR
 Return value: None
*************************************************/
void Lcd_Clear(u16 Color)               
{	
   unsigned int i,m;
   Lcd_SetRegion(0,0,X_MAX_PIXEL-1,Y_MAX_PIXEL-1);
   Lcd_WriteIndex(0x2C);
   for(i=0;i<X_MAX_PIXEL;i++)
    for(m=0;m<Y_MAX_PIXEL;m++)
    {	
	  	LCD_WriteData_16Bit(Color);
    }   
}

3. Delay function file delay.c

#include "stm32f4xx.h"
#include "delay.h" 
static u8  fac_us=0;//us delay multiplier
static u16 fac_ms=0;//ms delay multiplier
//Initialization delay function
//SYSTICK clock is fixed to 1 / 8 of HCLK clock
//SYSCLK: system clock
void delay_init(u8 SYSCLK)
{
	SysTick->CTRL&=0xfffffffb;//bit2 clear, select external clock HCLK/8
	fac_us=SYSCLK/8;		    
	fac_ms=(u16)fac_us*1000;
}								    
//Delay nms
//Note the range of nms
//Systick - > load is a 24 bit register, so the maximum delay is:
//nms<=0xffffff*8*1000/SYSCLK
//SYSCLK in Hz,nms in ms
//For 72M, NMS < = 1864 
void delay_ms(u16 nms)
{	 		  	  
	u32 temp;		   
	SysTick->LOAD=(u32)nms*fac_ms;//Time loading (systick - > load is 24bit)
	SysTick->VAL =0x00;           //Clear counter
	SysTick->CTRL=0x01 ;          //Countdown  
	do
	{
		temp=SysTick->CTRL;
	}
	while(temp&0x01&&!(temp&(1<<16)));//Waiting time arrives   
	SysTick->CTRL=0x00;       //Turn off counter
	SysTick->VAL =0X00;       //Clear counter	  	    
}   
//Delay nus
//nus is the number of us to delay		    								   
void delay_us(u32 nus)
{		
	u32 temp;	    	 
	SysTick->LOAD=nus*fac_us; //Time loading	  		 
	SysTick->VAL=0x00;        //Clear counter
	SysTick->CTRL=0x01 ;      //Countdown 	 
	do
	{
		temp=SysTick->CTRL;
	}
	while(temp&0x01&&!(temp&(1<<16)));//Waiting time arrives   
	SysTick->CTRL=0x00;       //Turn off counter
	SysTick->VAL =0X00;       //Clear counter	 
}

4. Image display driver file GUI.c

#include "stm32f4xx.h"
#include "Lcd_Driver.h"
#include "GUI.h"
#include "delay.h"
#include "font.h"
//The data read from ILI93xx is in GBR format, while we write in RGB format.
//Convert by this function
//c: Color value in GBR format
//Return value: RGB color value
u16 LCD_BGR2RGB(u16 c)
{
  u16  r,g,b,rgb;   
  b=(c>>0)&0x1f;
  g=(c>>5)&0x3f;
  r=(c>>11)&0x1f;	 
  rgb=(b<<11)+(g<<5)+(r<<0);		 
  return(rgb);

}
void Gui_Circle(u16 X,u16 Y,u16 R,u16 fc) 
{//Bresenham algorithm 
    unsigned short  a,b; 
    int c; 
    a=0; 
    b=R; 
    c=3-2*R; 
    while (a<b) 
    { 
        Gui_DrawPoint(X+a,Y+b,fc);     //        7 
        Gui_DrawPoint(X-a,Y+b,fc);     //        6 
        Gui_DrawPoint(X+a,Y-b,fc);     //        2 
        Gui_DrawPoint(X-a,Y-b,fc);     //        3 
        Gui_DrawPoint(X+b,Y+a,fc);     //        8 
        Gui_DrawPoint(X-b,Y+a,fc);     //        5 
        Gui_DrawPoint(X+b,Y-a,fc);     //        1 
        Gui_DrawPoint(X-b,Y-a,fc);     //        4 

        if(c<0) c=c+4*a+6; 
        else 
        { 
            c=c+4*(a-b)+10; 
            b-=1; 
        } 
       a+=1; 
    } 
    if (a==b) 
    { 
        Gui_DrawPoint(X+a,Y+b,fc); 
        Gui_DrawPoint(X+a,Y+b,fc); 
        Gui_DrawPoint(X+a,Y-b,fc); 
        Gui_DrawPoint(X-a,Y-b,fc); 
        Gui_DrawPoint(X+b,Y+a,fc); 
        Gui_DrawPoint(X-b,Y+a,fc); 
        Gui_DrawPoint(X+b,Y-a,fc); 
        Gui_DrawPoint(X-b,Y-a,fc); 
    } 
	
} 
//Line drawing function, using Bresenham line drawing algorithm
void Gui_DrawLine(u16 x0, u16 y0,u16 x1, u16 y1,u16 Color)   
{
int dx,             // difference in x's
    dy,             // difference in y's
    dx2,            // dx,dy * 2
    dy2, 
    x_inc,          // amount in pixel space to move during drawing
    y_inc,          // amount in pixel space to move during drawing
    error,          // the discriminant i.e. error i.e. decision variable
    index;          // used for looping	


	Lcd_SetXY(x0,y0);
	dx = x1-x0;//Calculate x distance
	dy = y1-y0;//Calculate y distance

	if (dx>=0)
	{
		x_inc = 1;
	}
	else
	{
		x_inc = -1;
		dx    = -dx;  
	} 
	
	if (dy>=0)
	{
		y_inc = 1;
	} 
	else
	{
		y_inc = -1;
		dy    = -dy; 
	} 

	dx2 = dx << 1;
	dy2 = dy << 1;

	if (dx > dy)//If x distance is greater than y distance, then there is only one point on each X axis and several points on each Y axis
	{//And the number of points of the line is equal to x distance, and the points are drawn in x-axis increments
		// initialize error term
		error = dy2 - dx; 

		// draw the line
		for (index=0; index <= dx; index++)//The number of points to be drawn will not exceed x distance
		{
			//Draw points
			Gui_DrawPoint(x0,y0,Color);
			
			// test if error has overflowed
			if (error >= 0) //Need to increase y coordinate value
			{
				error-=dx2;

				// move to next line
				y0+=y_inc;//Increase y coordinate value
			} // end if error overflowed

			// adjust the error term
			error+=dy2;

			// move to the next pixel
			x0+=x_inc;//The x coordinate value is increased by 1 every time the point is drawn
		} // end for
	} // end if |slope| <= 1
	else//If y-axis is larger than x-axis, there is only one point on each y-axis and several points on x-axis
	{//Draw points by increasing y axis
		// initialize error term
		error = dx2 - dy; 

		// draw the line
		for (index=0; index <= dy; index++)
		{
			// set the pixel
			Gui_DrawPoint(x0,y0,Color);

			// test if error overflowed
			if (error >= 0)
			{
				error-=dy2;

				// move to next line
				x0+=x_inc;
			} // end if error overflowed

			// adjust the error term
			error+=dx2;

			// move to the next pixel
			y0+=y_inc;
		} // end for
	} // end else |slope| > 1
}



void Gui_box(u16 x, u16 y, u16 w, u16 h,u16 bc)
{
	Gui_DrawLine(x,y,x+w,y,0xEF7D);
	Gui_DrawLine(x+w-1,y+1,x+w-1,y+1+h,0x2965);
	Gui_DrawLine(x,y+h,x+w,y+h,0x2965);
	Gui_DrawLine(x,y,x,y+h,0xEF7D);
    Gui_DrawLine(x+1,y+1,x+1+w-2,y+1+h-2,bc);
}
void Gui_box2(u16 x,u16 y,u16 w,u16 h, u8 mode)
{
	if (mode==0)	{
		Gui_DrawLine(x,y,x+w,y,0xEF7D);
		Gui_DrawLine(x+w-1,y+1,x+w-1,y+1+h,0x2965);
		Gui_DrawLine(x,y+h,x+w,y+h,0x2965);
		Gui_DrawLine(x,y,x,y+h,0xEF7D);
		}
	if (mode==1)	{
		Gui_DrawLine(x,y,x+w,y,0x2965);
		Gui_DrawLine(x+w-1,y+1,x+w-1,y+1+h,0xEF7D);
		Gui_DrawLine(x,y+h,x+w,y+h,0xEF7D);
		Gui_DrawLine(x,y,x,y+h,0x2965);
	}
	if (mode==2)	{
		Gui_DrawLine(x,y,x+w,y,0xffff);
		Gui_DrawLine(x+w-1,y+1,x+w-1,y+1+h,0xffff);
		Gui_DrawLine(x,y+h,x+w,y+h,0xffff);
		Gui_DrawLine(x,y,x,y+h,0xffff);
	}
}


/**************************************************************************************
Function Description: display a raised button box on the screen
 Input: u16 x1,y1,x2,y2 button box upper left and lower right coordinates
 Output: None
**************************************************************************************/
void DisplayButtonDown(u16 x1,u16 y1,u16 x2,u16 y2)
{
	Gui_DrawLine(x1,  y1,  x2,y1, GRAY2);  //H
	Gui_DrawLine(x1+1,y1+1,x2,y1+1, GRAY1);  //H
	Gui_DrawLine(x1,  y1,  x1,y2, GRAY2);  //V
	Gui_DrawLine(x1+1,y1+1,x1+1,y2, GRAY1);  //V
	Gui_DrawLine(x1,  y2,  x2,y2, WHITE);  //H
	Gui_DrawLine(x2,  y1,  x2,y2, WHITE);  //V
}

/**************************************************************************************
Function Description: display a concave button box on the screen
 Input: u16 x1,y1,x2,y2 button box upper left and lower right coordinates
 Output: None
**************************************************************************************/
void DisplayButtonUp(u16 x1,u16 y1,u16 x2,u16 y2)
{
	Gui_DrawLine(x1,  y1,  x2,y1, WHITE); //H
	Gui_DrawLine(x1,  y1,  x1,y2, WHITE); //V
	
	Gui_DrawLine(x1+1,y2-1,x2,y2-1, GRAY1);  //H
	Gui_DrawLine(x1,  y2,  x2,y2, GRAY2);  //H
	Gui_DrawLine(x2-1,y1+1,x2-1,y2, GRAY1);  //V
    Gui_DrawLine(x2  ,y1  ,x2,y2, GRAY2); //V
}


void Gui_DrawFont_GBK16(u16 x, u16 y, u16 fc, u16 bc, u8 *s)
{
	unsigned char i,j;
	unsigned short k,x0;
	x0=x;

	while(*s) 
	{	
		if((*s) < 128) 
		{
			k=*s;
			if (k==13) 
			{
				x=x0;
				y+=16;
			}
			else 
			{
				if (k>32) k-=32; else k=0;
	
			    for(i=0;i<16;i++)
				for(j=0;j<8;j++) 
					{
				    	if(asc16[k*16+i]&(0x80>>j))	Gui_DrawPoint(x+j,y+i,fc);
						else 
						{
							if (fc!=bc) Gui_DrawPoint(x+j,y+i,bc);
						}
					}
				x+=8;
			}
			s++;
		}
			
		else 
		{
		

			for (k=0;k<hz16_num;k++) 
			{
			  if ((hz16[k].Index[0]==*(s))&&(hz16[k].Index[1]==*(s+1)))
			  { 
				    for(i=0;i<16;i++)
				    {
						for(j=0;j<8;j++) 
							{
						    	if(hz16[k].Msk[i*2]&(0x80>>j))	Gui_DrawPoint(x+j,y+i,fc);
								else {
									if (fc!=bc) Gui_DrawPoint(x+j,y+i,bc);
								}
							}
						for(j=0;j<8;j++) 
							{
						    	if(hz16[k].Msk[i*2+1]&(0x80>>j))	Gui_DrawPoint(x+j+8,y+i,fc);
								else 
								{
									if (fc!=bc) Gui_DrawPoint(x+j+8,y+i,bc);
								}
							}
				    }
				}
			  }
			s+=2;x+=16;
		} 
		
	}
}

void Gui_DrawFont_GBK24(u16 x, u16 y, u16 fc, u16 bc, u8 *s)
{
	unsigned char i,j;
	unsigned short k;

	while(*s) 
	{
		if( *s < 0x80 ) 
		{
			k=*s;
			if (k>32) k-=32; else k=0;

		    for(i=0;i<16;i++)
			for(j=0;j<8;j++) 
				{
			    	if(asc16[k*16+i]&(0x80>>j))	
					Gui_DrawPoint(x+j,y+i,fc);
					else 
					{
						if (fc!=bc) Gui_DrawPoint(x+j,y+i,bc);
					}
				}
			s++;x+=8;
		}
		else 
		{

			for (k=0;k<hz24_num;k++) 
			{
			  if ((hz24[k].Index[0]==*(s))&&(hz24[k].Index[1]==*(s+1)))
			  { 
				    for(i=0;i<24;i++)
				    {
						for(j=0;j<8;j++) 
							{
						    	if(hz24[k].Msk[i*3]&(0x80>>j))
								Gui_DrawPoint(x+j,y+i,fc);
								else 
								{
									if (fc!=bc) Gui_DrawPoint(x+j,y+i,bc);
								}
							}
						for(j=0;j<8;j++) 
							{
						    	if(hz24[k].Msk[i*3+1]&(0x80>>j))	Gui_DrawPoint(x+j+8,y+i,fc);
								else {
									if (fc!=bc) Gui_DrawPoint(x+j+8,y+i,bc);
								}
							}
						for(j=0;j<8;j++) 
							{
						    	if(hz24[k].Msk[i*3+2]&(0x80>>j))	
								Gui_DrawPoint(x+j+16,y+i,fc);
								else 
								{
									if (fc!=bc) Gui_DrawPoint(x+j+16,y+i,bc);
								}
							}
				    }
			  }
			}
			s+=2;x+=24;
		}
	}
}
void Gui_DrawFont_Num32(u16 x, u16 y, u16 fc, u16 bc, u16 num)
{
	unsigned char i,j,k,c;
	//lcd_text_any(x+94+i*42,y+34,32,32,0x7E8,0x0,sz32,knum[i]);
//	w=w/8;

    for(i=0;i<32;i++)
	{
		for(j=0;j<4;j++) 
		{
			c=*(sz32+num*32*4+i*4+j);
			for (k=0;k<8;k++)	
			{
	
		    	if(c&(0x80>>k))	Gui_DrawPoint(x+j*8+k,y+i,fc);
				else {
					if (fc!=bc) Gui_DrawPoint(x+j*8+k,y+i,bc);
				}
			}
		}
	}
}

5. TFT display image file qdtft? Demo. C

#include "stm32f4xx.h"
#include "Lcd_Driver.h"
#include "GUI.h"
#include "delay.h"
#include "Picture.h"
#include "QDTFT_demo.h"
unsigned char Num[10]={0,1,2,3,4,5,6,7,8,9};
void Redraw_Mainmenu(void)
{

	Lcd_Clear(GRAY0);
	
	Gui_DrawFont_GBK16(48,0,BLUE,GRAY0,"CSDN");
	
//	DisplayButtonUp(15,18,113,28);
	Gui_DrawFont_GBK16(32,20,RED,GRAY0,"AXYZdong");

	DisplayButtonUp(15,38,113,58); //x1,y1,x2,y2
	Gui_DrawFont_GBK16(32,40,YELLOW,GRAY0,"Text display");

	DisplayButtonUp(15,68,113,88); //x1,y1,x2,y2
	Gui_DrawFont_GBK16(2,70,BLUE,GRAY0,"Tel:17855525056");

	DisplayButtonUp(15,98,113,118); //x1,y1,x2,y2
	Gui_DrawFont_GBK16(0,100,RED,GRAY0,"www.AXYZdong.com");
	delay_ms(1500);
}

void Num_Test(void)
{
	u8 i=0;
	Lcd_Clear(GRAY0);
	Gui_DrawFont_GBK16(32,60,RED,GRAY0,"Num Test");
	delay_ms(1000);
	Lcd_Clear(GRAY0);

	for(i=0;i<10;i++)
	{
	Gui_DrawFont_Num32((i%3)*42,32*(i/3),RED,GRAY0,Num[i+1]);
	delay_ms(100);
	}
	
}

void Font_Test(void)
{
	Lcd_Clear(GRAY0);
	Gui_DrawFont_GBK16(16,60,BLUE,GRAY0,"Text display test");

	delay_ms(1000);
	Lcd_Clear(GRAY0);
	Gui_DrawFont_GBK16(16,20,YELLOW,GRAY0,"Full motion electronic technology");
	Gui_DrawFont_GBK16(16,40,BLUE,GRAY0,"Focus on LCD wholesale");
	Gui_DrawFont_GBK16(16,60,RED,GRAY0, "Full technical support");
	Gui_DrawFont_GBK16(4,80,BLUE,GRAY0,"Tel:17855525056");
	Gui_DrawFont_GBK16(4,100,RED,GRAY0, "www.youdong.com");	
	delay_ms(1800);	
}

void Color_Test(void)
{
	u8 i=1;
	Lcd_Clear(GRAY0);
	
	Gui_DrawFont_GBK16(24,60,BLUE,GRAY0,"Color Test");
	delay_ms(200);

	while(i--)
	{
		Lcd_Clear(WHITE);
		Lcd_Clear(BLACK);
		Lcd_Clear(RED);
	  Lcd_Clear(GREEN);
	  Lcd_Clear(BLUE);
	}		
}

//Mode: horizontal scanning from left to right
void showimage(const unsigned char *p) //Display 40*40 QQ picture
{
  	int i,j,k; 
	unsigned char picH,picL;
	Lcd_Clear(WHITE); //Clean screen  
	
	for(k=0;k<3;k++)
	{
	   	for(j=0;j<3;j++)
		{	
			Lcd_SetRegion(40*j,40*k,40*j+39,40*k+39);		//Coordinate setting
		    for(i=0;i<40*40;i++)
			 {	
			 	picL=*(p+i*2);	//Data low in front
				picH=*(p+i*2+1);				
				LCD_WriteData_16Bit(picH<<8|picL);  						
			 }	
		 }
	}		
}

//Mode: horizontal scanning from left to right
void showphoto(const unsigned char *p) //Display 128 * 128 pictures
{
  	int i; 
	unsigned char picH,picL;
//	Lcd_clear (where); / / clear screen  
	
	Lcd_SetRegion(0,0,127,127);		//Coordinate setting
		for(i=0;i<128*128;i++)
	 {	
		picL=*(p+i*2);	//Data low in front
		picH=*(p+i*2+1);				
		LCD_WriteData_16Bit(picH<<8|picL);  						
	 }		
}
void QDTFT_Test_Demo(void)
{
//	Lcd_Init();
	LCD_LED_SET;//Control backlight via IO				
	Redraw_Mainmenu();//Draw main menu (some contents may not be displayed due to resolution exceeding physical value)
//	Color_Test(); / / simple solid color fill
//	Num_Test(); / / nixie tube font
//	Font_Test(); / / displayed in Chinese and English		
//	showphoto(gImage_Robotmaster); / / image display example
//	delay_ms(1200);
//	LCD? Led? CLR; / / Io control backlight off	
}

6. Main function main.c

//  By AXYZdong
//  Generated on: February 3, 2020
//  Latest revision: March 2, 2020 
//  Function Description: TFT SPI interface demonstration routine (stm32 Series)
//              GND power ground
//              VCC connected to 5V or 3.3v power supply
//              LED connect to PB9
//              SCL connect to PB10
//              SDA connect to PB12
//              RS connect to PB11
//              RST connect to PB14
//              CS connect to PB13               
//              ------------------------------------------------------------ 

/*Left--Right Pin:VCC GND GND NC NC LED SCL SDA RS RST CS*/

#include "stm32f4xx.h"
#include "delay.h"
#include "QDTFT_demo.h"
#include "Lcd_Driver.h"
#include "GUI.h"


int main(void)
{

  SystemInit(); 	//System init.
  delay_init(72);   //Delay init.
  Lcd_Init();
  while(1)
  {  
	QDTFT_Test_Demo();	//See the test details in QDTFT_Demo.c		
  }

}

There are a lot of codes on. If you don't know something, you can send it to me.
I took two pictures of the functions implemented in the above program, which can be seen.

Of course, display characters, Chinese characters and pictures are the most basic functions of TFT. As a display medium, if communication is established with other devices, the information generated by other devices will be displayed on TFT, so we can obtain the desired information intuitively.

So, how to establish a communication relationship with each other? How to display on TFT intuitively? It's what I want to explore and learn in the future. The blog will also be updated from time to time, and it is expected that some article will be updated to relevant content in the near future. (hhh, sell it first)

Next, more exciting!

It's not easy to code. Your support is the driving force for me to stick to it. Don't forget to pay attention to me!

Published 5 original articles, won praise 4, visitors 2124
Private letter follow

Posted by vtolbert on Mon, 02 Mar 2020 22:15:02 -0800