移植浦洋1.69触摸屏(基于hal库stm32f407zgt6)

news/2024/9/21 22:56:15

该款触摸屏幕显示芯片为:ST7789。触摸芯片为:CST816

一、所需文件

源文件来自于炸鸡派下的BSP下的TOUCH、LCD、IIC文件夹下的所有文件和SYS下的所有文件:

各个修改后的源文件为:

1.显示部分:

得手动配置硬件spi

lcdinit.h

#ifndef __LCD_INIT_H
#define __LCD_INIT_H#include "sys.h"#define USE_HORIZONTAL 0  //设置横屏或者竖屏显示 0或1为竖屏 2或3为横屏#if USE_HORIZONTAL==0||USE_HORIZONTAL==1
#define LCD_W 240
#define LCD_H 280#else
#define LCD_W 280
#define LCD_H 240
#endif//-----------------LCD端口定义---------------- 
#define RES_PORT			GPIOA
#define RES_PIN				GPIO_PIN_2#define DC_PORT				GPIOA
#define DC_PIN				GPIO_PIN_1#define CS_PORT				GPIOA
#define CS_PIN				GPIO_PIN_3// #define BLK_PORT			GPIOB
// #define BLK_PIN				GPIO_PIN_0#define LCD_RES_Clr()  HAL_GPIO_WritePin(RES_PORT,RES_PIN,GPIO_PIN_RESET)//RES
#define LCD_RES_Set()  HAL_GPIO_WritePin(RES_PORT,RES_PIN,GPIO_PIN_SET)#define LCD_DC_Clr()   HAL_GPIO_WritePin(DC_PORT,DC_PIN,GPIO_PIN_RESET)//DC
#define LCD_DC_Set()   HAL_GPIO_WritePin(DC_PORT,DC_PIN,GPIO_PIN_SET)#define LCD_CS_Clr()   HAL_GPIO_WritePin(CS_PORT,CS_PIN,GPIO_PIN_RESET)//CS
#define LCD_CS_Set()   HAL_GPIO_WritePin(CS_PORT,CS_PIN,GPIO_PIN_SET)// #define LCD_BLK_Clr()  HAL_GPIO_WritePin(BLK_PORT,BLK_PIN,GPIO_PIN_RESET)//BLK
// #define LCD_BLK_Set()  HAL_GPIO_WritePin(BLK_PORT,BLK_PIN,GPIO_PIN_SET)void LCD_GPIO_Init(void);//初始化GPIO
void LCD_Writ_Bus(u8 dat);//模拟SPI时序
void LCD_WR_DATA8(u8 dat);//写入一个字节
void LCD_WR_DATA(u16 dat);//写入两个字节
void LCD_WR_REG(u8 dat);//写入一个指令
void LCD_Address_Set(u16 x1,u16 y1,u16 x2,u16 y2);//设置坐标函数
void LCD_Init(void);//LCD初始化
void LCD_ST7789_SleepIn(void);
void LCD_ST7789_SleepOut(void);#endif

lcdinit.c

#include "lcd_init.h"
#include "delay.h"
#include "spi.h"/******************************************************************************函数说明:LCD端口初始化入口数据:无返回值:  无
******************************************************************************/
void LCD_GPIO_Init(void)
{GPIO_InitTypeDef  GPIO_InitStructure = {0};__HAL_RCC_GPIOB_CLK_ENABLE();GPIO_InitStructure.Pin = RES_PIN|CS_PIN|DC_PIN;	 GPIO_InitStructure.Mode = GPIO_MODE_OUTPUT_PP; 		 //推挽输出GPIO_InitStructure.Speed = GPIO_SPEED_FREQ_VERY_HIGH;//速度50MHzHAL_GPIO_Init(GPIOB, &GPIO_InitStructure);	  //初始化GPIOBHAL_GPIO_WritePin(GPIOB, RES_PIN|CS_PIN|DC_PIN, GPIO_PIN_SET);
}/******************************************************************************函数说明:LCD串行数据写入函数(software SPI)入口数据:dat  要写入的串行数据返回值:  无
******************************************************************************/
void LCD_Writ_Bus(u8 dat) 
{	//hard SPIHAL_SPI_Transmit(&hspi1,&dat,1,1);//soft SPI/*u8 i;for(i=0;i<8;i++){			  LCD_SCLK_Clr();if(dat&0x80){LCD_MOSI_Set();}else{LCD_MOSI_Clr();}LCD_SCLK_Set();dat<<=1;}	*/
}/******************************************************************************函数说明:LCD写入数据入口数据:dat 写入的数据返回值:  无
******************************************************************************/
void LCD_WR_DATA8(u8 dat)
{LCD_Writ_Bus(dat);
}/******************************************************************************函数说明:LCD写入数据入口数据:dat 写入的数据返回值:  无
******************************************************************************/
void LCD_WR_DATA(u16 dat)
{
//	LCD_Writ_Bus(dat>>8);
//	LCD_Writ_Bus(dat);uint8_t temp[2];temp[0]=(dat>>8)&0xff;temp[1]=dat&0xff;HAL_SPI_Transmit(&hspi1,temp,2,1);}/******************************************************************************函数说明:LCD写入命令入口数据:dat 写入的命令返回值:  无
******************************************************************************/
void LCD_WR_REG(u8 dat)
{LCD_DC_Clr();//写命令LCD_Writ_Bus(dat);LCD_DC_Set();//写数据
}/******************************************************************************函数说明:设置起始和结束地址入口数据:x1,x2 设置列的起始和结束地址y1,y2 设置行的起始和结束地址返回值:  无
******************************************************************************/
void LCD_Address_Set(u16 x1,u16 y1,u16 x2,u16 y2)
{LCD_WR_REG(0x2a);//列地址设置LCD_WR_DATA(x1);LCD_WR_DATA(x2);LCD_WR_REG(0x2b);//行地址设置LCD_WR_DATA(y1);LCD_WR_DATA(y2);LCD_WR_REG(0x2c);//储存器写
}/******************************************************************************函数说明:ST7789 SLEEP IN入口数据:无返回值:  无
******************************************************************************/
void LCD_ST7789_SleepIn(void)
{LCD_WR_REG(0x10);delay_ms(100);
}/******************************************************************************函数说明:ST7789 SLEEP OUT入口数据:无返回值:  无
******************************************************************************/
void LCD_ST7789_SleepOut(void)
{LCD_WR_REG(0x11);delay_ms(100);
}/******************************************************************************函数说明:LCD初始化入口数据:无返回值:  无
******************************************************************************/
void LCD_Init(void)
{//LCD_GPIO_Init();//初始化GPIOHAL_GPIO_WritePin(GPIOA, RES_PIN|CS_PIN|DC_PIN, GPIO_PIN_SET);LCD_CS_Clr();		//chip selectLCD_RES_Clr();	//复位delay_ms(100);LCD_RES_Set();delay_ms(100);LCD_WR_REG(0x11); delay_ms(120); LCD_WR_REG(0x36); if(USE_HORIZONTAL==0)LCD_WR_DATA8(0x00);else if(USE_HORIZONTAL==1)LCD_WR_DATA8(0xC0);else if(USE_HORIZONTAL==2)LCD_WR_DATA8(0x70);else LCD_WR_DATA8(0xA0);LCD_WR_REG(0x3A);LCD_WR_DATA8(0x05);LCD_WR_REG(0xB2);LCD_WR_DATA8(0x0C);LCD_WR_DATA8(0x0C);LCD_WR_DATA8(0x00);LCD_WR_DATA8(0x33);LCD_WR_DATA8(0x33); LCD_WR_REG(0xB7); LCD_WR_DATA8(0x35);  LCD_WR_REG(0xBB);LCD_WR_DATA8(0x19);LCD_WR_REG(0xC0);LCD_WR_DATA8(0x2C);LCD_WR_REG(0xC2);LCD_WR_DATA8(0x01);LCD_WR_REG(0xC3);LCD_WR_DATA8(0x12);   LCD_WR_REG(0xC4);LCD_WR_DATA8(0x20);  LCD_WR_REG(0xC6); LCD_WR_DATA8(0x0F);    LCD_WR_REG(0xD0); LCD_WR_DATA8(0xA4);LCD_WR_DATA8(0xA1);LCD_WR_REG(0xE0);LCD_WR_DATA8(0xD0);LCD_WR_DATA8(0x04);LCD_WR_DATA8(0x0D);LCD_WR_DATA8(0x11);LCD_WR_DATA8(0x13);LCD_WR_DATA8(0x2B);LCD_WR_DATA8(0x3F);LCD_WR_DATA8(0x54);LCD_WR_DATA8(0x4C);LCD_WR_DATA8(0x18);LCD_WR_DATA8(0x0D);LCD_WR_DATA8(0x0B);LCD_WR_DATA8(0x1F);LCD_WR_DATA8(0x23);LCD_WR_REG(0xE1);LCD_WR_DATA8(0xD0);LCD_WR_DATA8(0x04);LCD_WR_DATA8(0x0C);LCD_WR_DATA8(0x11);LCD_WR_DATA8(0x13);LCD_WR_DATA8(0x2C);LCD_WR_DATA8(0x3F);LCD_WR_DATA8(0x44);LCD_WR_DATA8(0x51);LCD_WR_DATA8(0x2F);LCD_WR_DATA8(0x1F);LCD_WR_DATA8(0x1F);LCD_WR_DATA8(0x20);LCD_WR_DATA8(0x23);LCD_WR_REG(0x21); LCD_WR_REG(0x29); 
}

lcd.h

#ifndef __LCD_H
#define __LCD_H		
#include "sys.h"void LCD_Fill(u16 xsta,u16 ysta,u16 xend,u16 yend,u16 color);//指定区域填充颜色
void LCD_Color_Fill(u16 xsta,u16 ysta,u16 xend,u16 yend,u16 *color);
void LCD_DrawPoint(u16 x,u16 y,u16 color);//在指定位置画一个点
void LCD_DrawLine(u16 x1,u16 y1,u16 x2,u16 y2,u16 color);//在指定位置画一条线
void LCD_DrawRectangle(u16 x1, u16 y1, u16 x2, u16 y2,u16 color);//在指定位置画一个矩形
void Draw_Circle(u16 x0,u16 y0,u8 r,u16 color);//在指定位置画一个圆void LCD_ShowChinese(u16 x,u16 y,u8 *s,u16 fc,u16 bc,u8 sizey,u8 mode);//显示汉字串
void LCD_ShowChinese12x12(u16 x,u16 y,u8 *s,u16 fc,u16 bc,u8 sizey,u8 mode);//显示单个12x12汉字
void LCD_ShowChinese16x16(u16 x,u16 y,u8 *s,u16 fc,u16 bc,u8 sizey,u8 mode);//显示单个16x16汉字
void LCD_ShowChinese24x24(u16 x,u16 y,u8 *s,u16 fc,u16 bc,u8 sizey,u8 mode);//显示单个24x24汉字
void LCD_ShowChinese32x32(u16 x,u16 y,u8 *s,u16 fc,u16 bc,u8 sizey,u8 mode);//显示单个32x32汉字void LCD_ShowChar(u16 x,u16 y,u8 num,u16 fc,u16 bc,u8 sizey,u8 mode);//显示一个字符
void LCD_ShowString(u16 x,u16 y,const u8 *p,u16 fc,u16 bc,u8 sizey,u8 mode);//显示字符串
u32 mypow(u8 m,u8 n);//求幂
void LCD_ShowIntNum(u16 x,u16 y,u16 num,u8 len,u16 fc,u16 bc,u8 sizey);//显示整数变量
void LCD_ShowFloatNum1(u16 x,u16 y,float num,u8 len,u16 fc,u16 bc,u8 sizey);//显示两位小数变量void LCD_ShowPicture(u16 x,u16 y,u16 length,u16 width,const u8 pic[]);//显示图片//画笔颜色
#define WHITE         	 0xFFFF
#define BLACK         	 0x0000	  
#define BLUE           	 0x001F  
#define BRED             0XF81F
#define GRED 			       0XFFE0
#define GBLUE			       0X07FF
#define RED           	 0xF800
#define MAGENTA       	 0xF81F
#define GREEN         	 0x07E0
#define CYAN          	 0x7FFF
#define YELLOW        	 0xFFE0
#define BROWN 			     0XBC40 //棕色
#define BRRED 			     0XFC07 //棕红色
#define GRAY  			     0X8430 //灰色
#define DARKBLUE      	 0X01CF	//深蓝色
#define LIGHTBLUE      	 0X7D7C	//浅蓝色  
#define GRAYBLUE       	 0X5458 //灰蓝色
#define LIGHTGREEN     	 0X841F //浅绿色
#define LGRAY 			     0XC618 //浅灰色(PANNEL),窗体背景色
#define LGRAYBLUE        0XA651 //浅灰蓝色(中间层颜色)
#define LBBLUE           0X2B12 //浅棕蓝色(选择条目的反色)#endif

lcd.c

#include "lcd.h"
#include "lcd_init.h"
#include "lcdfont.h"
#include "delay.h"
#include "spi.h"#define OFFSET_Y 20/******************************************************************************函数说明:在指定区域填充颜色入口数据:xsta,ysta   起始坐标xend,yend   终止坐标color       要填充的颜色返回值:  无
******************************************************************************/
void LCD_Fill(u16 xsta,u16 ysta,u16 xend,u16 yend,u16 color)
{          u16 i,j; LCD_Address_Set(xsta,ysta+OFFSET_Y,xend-1,yend-1+OFFSET_Y);//设置显示范围for(i=ysta;i<yend;i++){		for(j=xsta;j<xend;j++){LCD_WR_DATA(color);}} 					  	    
}/******************************************************************************函数说明:在指定区域填充颜色入口数据:xsta,ysta   起始坐标xend,yend   终止坐标color       要填充的颜色返回值:  无
******************************************************************************/
void LCD_Color_Fill(u16 xsta,u16 ysta,u16 xend,u16 yend,u16 *color_p)
{u16 i,j,width,height; width = xend-xsta+1;height = yend-ysta+1;uint32_t size = width * height;LCD_Address_Set(xsta,ysta+OFFSET_Y,xend,yend+OFFSET_Y);hspi1.Init.DataSize = SPI_DATASIZE_16BIT;hspi1.Instance->CR1|=SPI_CR1_DFF;//HAL_SPI_Transmit_DMA(&hspi1,(uint8_t*)color_p,size);//while(__HAL_DMA_GET_COUNTER(&hdma_spi1_tx)!=0);hspi1.Init.DataSize = SPI_DATASIZE_8BIT;hspi1.Instance->CR1&=~SPI_CR1_DFF;}/******************************************************************************函数说明:在指定位置画点入口数据:x,y 画点坐标color 点的颜色返回值:  无
******************************************************************************/
void LCD_DrawPoint(u16 x,u16 y,u16 color)
{LCD_Address_Set(x,y,x,y);//设置光标位置 LCD_WR_DATA(color);
} /******************************************************************************函数说明:画线入口数据:x1,y1   起始坐标x2,y2   终止坐标color   线的颜色返回值:  无
******************************************************************************/
void LCD_DrawLine(u16 x1,u16 y1,u16 x2,u16 y2,u16 color)
{u16 t; int xerr=0,yerr=0,delta_x,delta_y,distance;int incx,incy,uRow,uCol;delta_x=x2-x1; //计算坐标增量 delta_y=y2-y1;uRow=x1;//画线起点坐标uCol=y1;if(delta_x>0)incx=1; //设置单步方向 else if (delta_x==0)incx=0;//垂直线 else {incx=-1;delta_x=-delta_x;}if(delta_y>0)incy=1;else if (delta_y==0)incy=0;//水平线 else {incy=-1;delta_y=-delta_y;}if(delta_x>delta_y)distance=delta_x; //选取基本增量坐标轴 else distance=delta_y;for(t=0;t<distance+1;t++){LCD_DrawPoint(uRow,uCol,color);//画点xerr+=delta_x;yerr+=delta_y;if(xerr>distance){xerr-=distance;uRow+=incx;}if(yerr>distance){yerr-=distance;uCol+=incy;}}
}/******************************************************************************函数说明:画矩形入口数据:x1,y1   起始坐标x2,y2   终止坐标color   矩形的颜色返回值:  无
******************************************************************************/
void LCD_DrawRectangle(u16 x1, u16 y1, u16 x2, u16 y2,u16 color)
{LCD_DrawLine(x1,y1,x2,y1,color);LCD_DrawLine(x1,y1,x1,y2,color);LCD_DrawLine(x1,y2,x2,y2,color);LCD_DrawLine(x2,y1,x2,y2,color);
}/******************************************************************************函数说明:画圆入口数据:x0,y0   圆心坐标r       半径color   圆的颜色返回值:  无
******************************************************************************/
void Draw_Circle(u16 x0,u16 y0,u8 r,u16 color)
{int a,b;a=0;b=r;	  while(a<=b){LCD_DrawPoint(x0-b,y0-a,color);             //3           LCD_DrawPoint(x0+b,y0-a,color);             //0           LCD_DrawPoint(x0-a,y0+b,color);             //1                LCD_DrawPoint(x0-a,y0-b,color);             //2             LCD_DrawPoint(x0+b,y0+a,color);             //4               LCD_DrawPoint(x0+a,y0-b,color);             //5LCD_DrawPoint(x0+a,y0+b,color);             //6 LCD_DrawPoint(x0-b,y0+a,color);             //7a++;if((a*a+b*b)>(r*r))//判断要画的点是否过远{b--;}}
}/******************************************************************************函数说明:显示汉字串入口数据:x,y显示坐标*s 要显示的汉字串fc 字的颜色bc 字的背景色sizey 字号 可选 16 24 32mode:  0非叠加模式  1叠加模式返回值:  无
******************************************************************************/
void LCD_ShowChinese(u16 x,u16 y,u8 *s,u16 fc,u16 bc,u8 sizey,u8 mode)
{while(*s!=0){if(sizey==12) LCD_ShowChinese12x12(x,y,s,fc,bc,sizey,mode);else if(sizey==16) LCD_ShowChinese16x16(x,y,s,fc,bc,sizey,mode);else if(sizey==24) LCD_ShowChinese24x24(x,y,s,fc,bc,sizey,mode);else if(sizey==32) LCD_ShowChinese32x32(x,y,s,fc,bc,sizey,mode);else return;s+=2;x+=sizey;}
}/******************************************************************************函数说明:显示单个12x12汉字入口数据:x,y显示坐标*s 要显示的汉字fc 字的颜色bc 字的背景色sizey 字号mode:  0非叠加模式  1叠加模式返回值:  无
******************************************************************************/
void LCD_ShowChinese12x12(u16 x,u16 y,u8 *s,u16 fc,u16 bc,u8 sizey,u8 mode)
{u8 i,j,m=0;u16 k;u16 HZnum;//汉字数目u16 TypefaceNum;//一个字符所占字节大小u16 x0=x;TypefaceNum=(sizey/8+((sizey%8)?1:0))*sizey;HZnum=sizeof(tfont12)/sizeof(typFNT_GB12);	//统计汉字数目for(k=0;k<HZnum;k++) {if((tfont12[k].Index[0]==*(s))&&(tfont12[k].Index[1]==*(s+1))){ 	LCD_Address_Set(x,y,x+sizey-1,y+sizey-1);for(i=0;i<TypefaceNum;i++){for(j=0;j<8;j++){	if(!mode)//非叠加方式{if(tfont12[k].Msk[i]&(0x01<<j))LCD_WR_DATA(fc);else LCD_WR_DATA(bc);m++;if(m%sizey==0){m=0;break;}}else//叠加方式{if(tfont12[k].Msk[i]&(0x01<<j))	LCD_DrawPoint(x,y,fc);//画一个点x++;if((x-x0)==sizey){x=x0;y++;break;}}}}}				  	continue;  //查找到对应点阵字库立即退出,防止多个汉字重复取模带来影响}
} /******************************************************************************函数说明:显示单个16x16汉字入口数据:x,y显示坐标*s 要显示的汉字fc 字的颜色bc 字的背景色sizey 字号mode:  0非叠加模式  1叠加模式返回值:  无
******************************************************************************/
void LCD_ShowChinese16x16(u16 x,u16 y,u8 *s,u16 fc,u16 bc,u8 sizey,u8 mode)
{u8 i,j,m=0;u16 k;u16 HZnum;//汉字数目u16 TypefaceNum;//一个字符所占字节大小u16 x0=x;TypefaceNum=(sizey/8+((sizey%8)?1:0))*sizey;HZnum=sizeof(tfont16)/sizeof(typFNT_GB16);	//统计汉字数目for(k=0;k<HZnum;k++) {if ((tfont16[k].Index[0]==*(s))&&(tfont16[k].Index[1]==*(s+1))){ 	LCD_Address_Set(x,y,x+sizey-1,y+sizey-1);for(i=0;i<TypefaceNum;i++){for(j=0;j<8;j++){	if(!mode)//非叠加方式{if(tfont16[k].Msk[i]&(0x01<<j))LCD_WR_DATA(fc);else LCD_WR_DATA(bc);m++;if(m%sizey==0){m=0;break;}}else//叠加方式{if(tfont16[k].Msk[i]&(0x01<<j))	LCD_DrawPoint(x,y,fc);//画一个点x++;if((x-x0)==sizey){x=x0;y++;break;}}}}}				  	continue;  //查找到对应点阵字库立即退出,防止多个汉字重复取模带来影响}
} /******************************************************************************函数说明:显示单个24x24汉字入口数据:x,y显示坐标*s 要显示的汉字fc 字的颜色bc 字的背景色sizey 字号mode:  0非叠加模式  1叠加模式返回值:  无
******************************************************************************/
void LCD_ShowChinese24x24(u16 x,u16 y,u8 *s,u16 fc,u16 bc,u8 sizey,u8 mode)
{u8 i,j,m=0;u16 k;u16 HZnum;//汉字数目u16 TypefaceNum;//一个字符所占字节大小u16 x0=x;TypefaceNum=(sizey/8+((sizey%8)?1:0))*sizey;HZnum=sizeof(tfont24)/sizeof(typFNT_GB24);	//统计汉字数目for(k=0;k<HZnum;k++) {if ((tfont24[k].Index[0]==*(s))&&(tfont24[k].Index[1]==*(s+1))){ 	LCD_Address_Set(x,y,x+sizey-1,y+sizey-1);for(i=0;i<TypefaceNum;i++){for(j=0;j<8;j++){	if(!mode)//非叠加方式{if(tfont24[k].Msk[i]&(0x01<<j))LCD_WR_DATA(fc);else LCD_WR_DATA(bc);m++;if(m%sizey==0){m=0;break;}}else//叠加方式{if(tfont24[k].Msk[i]&(0x01<<j))	LCD_DrawPoint(x,y,fc);//画一个点x++;if((x-x0)==sizey){x=x0;y++;break;}}}}}				  	continue;  //查找到对应点阵字库立即退出,防止多个汉字重复取模带来影响}
} /******************************************************************************函数说明:显示单个32x32汉字入口数据:x,y显示坐标*s 要显示的汉字fc 字的颜色bc 字的背景色sizey 字号mode:  0非叠加模式  1叠加模式返回值:  无
******************************************************************************/
void LCD_ShowChinese32x32(u16 x,u16 y,u8 *s,u16 fc,u16 bc,u8 sizey,u8 mode)
{u8 i,j,m=0;u16 k;u16 HZnum;//汉字数目u16 TypefaceNum;//一个字符所占字节大小u16 x0=x;TypefaceNum=(sizey/8+((sizey%8)?1:0))*sizey;HZnum=sizeof(tfont32)/sizeof(typFNT_GB32);	//统计汉字数目for(k=0;k<HZnum;k++) {if ((tfont32[k].Index[0]==*(s))&&(tfont32[k].Index[1]==*(s+1))){ 	LCD_Address_Set(x,y,x+sizey-1,y+sizey-1);for(i=0;i<TypefaceNum;i++){for(j=0;j<8;j++){	if(!mode)//非叠加方式{if(tfont32[k].Msk[i]&(0x01<<j))LCD_WR_DATA(fc);else LCD_WR_DATA(bc);m++;if(m%sizey==0){m=0;break;}}else//叠加方式{if(tfont32[k].Msk[i]&(0x01<<j))	LCD_DrawPoint(x,y,fc);//画一个点x++;if((x-x0)==sizey){x=x0;y++;break;}}}}}				  	continue;  //查找到对应点阵字库立即退出,防止多个汉字重复取模带来影响}
}/******************************************************************************函数说明:显示单个字符入口数据:x,y显示坐标num 要显示的字符fc 字的颜色bc 字的背景色sizey 字号mode:  0非叠加模式  1叠加模式返回值:  无
******************************************************************************/
void LCD_ShowChar(u16 x,u16 y,u8 num,u16 fc,u16 bc,u8 sizey,u8 mode)
{u8 temp,sizex,t,m=0;u16 i,TypefaceNum;//一个字符所占字节大小u16 x0=x;sizex=sizey/2;TypefaceNum=(sizex/8+((sizex%8)?1:0))*sizey;num=num-' ';    //得到偏移后的值LCD_Address_Set(x,y,x+sizex-1,y+sizey-1);  //设置光标位置 for(i=0;i<TypefaceNum;i++){ if(sizey==12)temp=ascii_1206[num][i];		       //调用6x12字体else if(sizey==16)temp=ascii_1608[num][i];		 //调用8x16字体else if(sizey==24)temp=ascii_2412[num][i];		 //调用12x24字体else if(sizey==32)temp=ascii_3216[num][i];		 //调用16x32字体else return;for(t=0;t<8;t++){if(!mode)//非叠加模式{if(temp&(0x01<<t))LCD_WR_DATA(fc);else LCD_WR_DATA(bc);m++;if(m%sizex==0){m=0;break;}}else//叠加模式{if(temp&(0x01<<t))LCD_DrawPoint(x,y,fc);//画一个点x++;if((x-x0)==sizex){x=x0;y++;break;}}}}   	 	  
}/******************************************************************************函数说明:显示字符串入口数据:x,y显示坐标*p 要显示的字符串fc 字的颜色bc 字的背景色sizey 字号mode:  0非叠加模式  1叠加模式返回值:  无
******************************************************************************/
void LCD_ShowString(u16 x,u16 y,const u8 *p,u16 fc,u16 bc,u8 sizey,u8 mode)
{         while(*p!='\0'){       LCD_ShowChar(x,y,*p,fc,bc,sizey,mode);x+=sizey/2;p++;}  
}/******************************************************************************函数说明:显示数字入口数据:m底数,n指数返回值:  无
******************************************************************************/
u32 mypow(u8 m,u8 n)
{u32 result=1;	 while(n--)result*=m;return result;
}/******************************************************************************函数说明:显示整数变量入口数据:x,y显示坐标num 要显示整数变量len 要显示的位数fc 字的颜色bc 字的背景色sizey 字号返回值:  无
******************************************************************************/
void LCD_ShowIntNum(u16 x,u16 y,u16 num,u8 len,u16 fc,u16 bc,u8 sizey)
{         	u8 t,temp;u8 enshow=0;u8 sizex=sizey/2;for(t=0;t<len;t++){temp=(num/mypow(10,len-t-1))%10;if(enshow==0&&t<(len-1)){if(temp==0){LCD_ShowChar(x+t*sizex,y,' ',fc,bc,sizey,0);continue;}else enshow=1; }LCD_ShowChar(x+t*sizex,y,temp+48,fc,bc,sizey,0);}
} /******************************************************************************函数说明:显示两位小数变量入口数据:x,y显示坐标num 要显示小数变量len 要显示的位数fc 字的颜色bc 字的背景色sizey 字号返回值:  无
******************************************************************************/
void LCD_ShowFloatNum1(u16 x,u16 y,float num,u8 len,u16 fc,u16 bc,u8 sizey)
{         	u8 t,temp,sizex;u16 num1;sizex=sizey/2;num1=num*100;for(t=0;t<len;t++){temp=(num1/mypow(10,len-t-1))%10;if(t==(len-2)){LCD_ShowChar(x+(len-2)*sizex,y,'.',fc,bc,sizey,0);t++;len+=1;}LCD_ShowChar(x+t*sizex,y,temp+48,fc,bc,sizey,0);}
}/******************************************************************************函数说明:显示图片入口数据:x,y起点坐标length 图片长度width  图片宽度pic[]  图片数组    返回值:  无
******************************************************************************/
void LCD_ShowPicture(u16 x,u16 y,u16 length,u16 width,const u8 pic[])
{u16 i,j;u32 k=0;LCD_Address_Set(x,y,x+length-1,y+width-1);for(i=0;i<length;i++){for(j=0;j<width;j++){LCD_WR_DATA8(pic[k*2]);LCD_WR_DATA8(pic[k*2+1]);k++;}}			
}
2.触摸部分

配置软件IIC

iic_hal.h

#ifndef __IIC_HAL_H
#define __IIC_HAL_H#include "stm32f4xx_hal.h"typedef struct
{GPIO_TypeDef * IIC_SDA_PORT;GPIO_TypeDef * IIC_SCL_PORT;uint16_t IIC_SDA_PIN;uint16_t IIC_SCL_PIN;//void (*CLK_ENABLE)(void);
}iic_bus_t;void IICStart(iic_bus_t *bus);
void IICStop(iic_bus_t *bus);
unsigned char IICWaitAck(iic_bus_t *bus);
void IICSendAck(iic_bus_t *bus);
void IICSendNotAck(iic_bus_t *bus);
void IICSendByte(iic_bus_t *bus, unsigned char cSendByte);
unsigned char IICReceiveByte(iic_bus_t *bus);
void IICInit(iic_bus_t *bus);uint8_t IIC_Write_One_Byte(iic_bus_t *bus, uint8_t daddr,uint8_t reg,uint8_t data);
uint8_t IIC_Write_Multi_Byte(iic_bus_t *bus, uint8_t daddr,uint8_t reg,uint8_t length,uint8_t buff[]);
unsigned char IIC_Read_One_Byte(iic_bus_t *bus, uint8_t daddr,uint8_t reg);
uint8_t IIC_Read_Multi_Byte(iic_bus_t *bus, uint8_t daddr, uint8_t reg, uint8_t length, uint8_t buff[]);
#endif

iic_hal.c

#include "iic_hal.h"
#include "delay.h"/*** @brief SDA线输入模式配置* @param None* @retval None*/
void SDA_Input_Mode(iic_bus_t *bus)
{GPIO_InitTypeDef GPIO_InitStructure = {0};GPIO_InitStructure.Pin = bus->IIC_SDA_PIN;GPIO_InitStructure.Mode = GPIO_MODE_INPUT;GPIO_InitStructure.Pull = GPIO_PULLUP;GPIO_InitStructure.Speed = GPIO_SPEED_FREQ_HIGH;HAL_GPIO_Init(bus->IIC_SDA_PORT, &GPIO_InitStructure);
}/*** @brief SDA线输出模式配置* @param None* @retval None*/
void SDA_Output_Mode(iic_bus_t *bus)
{GPIO_InitTypeDef GPIO_InitStructure = {0};GPIO_InitStructure.Pin = bus->IIC_SDA_PIN;GPIO_InitStructure.Mode = GPIO_MODE_OUTPUT_OD;GPIO_InitStructure.Pull = GPIO_NOPULL;GPIO_InitStructure.Speed = GPIO_SPEED_FREQ_HIGH;HAL_GPIO_Init(bus->IIC_SDA_PORT, &GPIO_InitStructure);
}/*** @brief SDA线输出一个位* @param val 输出的数据* @retval None*/
void SDA_Output(iic_bus_t *bus, uint16_t val)
{if ( val ){bus->IIC_SDA_PORT->BSRR |= bus->IIC_SDA_PIN;}else{bus->IIC_SDA_PORT->BSRR = (uint32_t)bus->IIC_SDA_PIN << 16U;}
}/*** @brief SCL线输出一个位* @param val 输出的数据* @retval None*/
void SCL_Output(iic_bus_t *bus, uint16_t val)
{if ( val ){bus->IIC_SCL_PORT->BSRR |= bus->IIC_SCL_PIN;}else{bus->IIC_SCL_PORT->BSRR = (uint32_t)bus->IIC_SCL_PIN << 16U;}
}/*** @brief SDA输入一位* @param None* @retval GPIO读入一位*/
uint8_t SDA_Input(iic_bus_t *bus)
{if(HAL_GPIO_ReadPin(bus->IIC_SDA_PORT, bus->IIC_SDA_PIN) == GPIO_PIN_SET){return 1;}else{return 0;}
}/*** @brief IIC起始信号* @param None* @retval None*/
void IICStart(iic_bus_t *bus)
{SDA_Output(bus,1);//delay1(DELAY_TIME);delay_us(2);SCL_Output(bus,1);delay_us(1);SDA_Output(bus,0);delay_us(1);SCL_Output(bus,0);delay_us(1);
}/*** @brief IIC结束信号* @param None* @retval None*/
void IICStop(iic_bus_t *bus)
{SCL_Output(bus,0);delay_us(2);SDA_Output(bus,0);delay_us(1);SCL_Output(bus,1);delay_us(1);SDA_Output(bus,1);delay_us(1);}/*** @brief IIC等待确认信号* @param None* @retval None*/
unsigned char IICWaitAck(iic_bus_t *bus)
{unsigned short cErrTime = 5;SDA_Input_Mode(bus);SCL_Output(bus,1);while(SDA_Input(bus)){cErrTime--;delay_us(1);if (0 == cErrTime){SDA_Output_Mode(bus);IICStop(bus);return ERROR;}}SDA_Output_Mode(bus);SCL_Output(bus,0);delay_us(2);return SUCCESS;
}/*** @brief IIC发送确认信号* @param None* @retval None*/
void IICSendAck(iic_bus_t *bus)
{SDA_Output(bus,0);delay_us(1);SCL_Output(bus,1);delay_us(1);SCL_Output(bus,0);delay_us(1);}/*** @brief IIC发送非确认信号* @param None* @retval None*/
void IICSendNotAck(iic_bus_t *bus)
{SDA_Output(bus,1);delay_us(1);SCL_Output(bus,1);delay_us(1);SCL_Output(bus,0);delay_us(2);}/*** @brief IIC发送一个字节* @param cSendByte 需要发送的字节* @retval None*/
void IICSendByte(iic_bus_t *bus,unsigned char cSendByte)
{unsigned char  i = 8;while (i--){SCL_Output(bus,0);delay_us(2);SDA_Output(bus, cSendByte & 0x80);delay_us(1);cSendByte += cSendByte;delay_us(1);SCL_Output(bus,1);delay_us(1);}SCL_Output(bus,0);delay_us(2);
}/*** @brief IIC接收一个字节* @param None* @retval 接收到的字节*/
unsigned char IICReceiveByte(iic_bus_t *bus)
{unsigned char i = 8;unsigned char cR_Byte = 0;SDA_Input_Mode(bus);while (i--){cR_Byte += cR_Byte;SCL_Output(bus,0);delay_us(2);SCL_Output(bus,1);delay_us(1);cR_Byte |=  SDA_Input(bus);}SCL_Output(bus,0);SDA_Output_Mode(bus);return cR_Byte;
}uint8_t IIC_Write_One_Byte(iic_bus_t *bus, uint8_t daddr,uint8_t reg,uint8_t data)
{				   	  	    																 IICStart(bus);  IICSendByte(bus,daddr<<1);	    if(IICWaitAck(bus))	//等待应答{IICStop(bus);		 return 1;		}IICSendByte(bus,reg);IICWaitAck(bus);	   	 										  		   IICSendByte(bus,data);     						   IICWaitAck(bus);  		    	   IICStop(bus);delay_us(1);return 0;
}uint8_t IIC_Write_Multi_Byte(iic_bus_t *bus, uint8_t daddr,uint8_t reg,uint8_t length,uint8_t buff[])
{			unsigned char i;	IICStart(bus);  IICSendByte(bus,daddr<<1);	    if(IICWaitAck(bus)){IICStop(bus);return 1;}IICSendByte(bus,reg);IICWaitAck(bus);	for(i=0;i<length;i++){IICSendByte(bus,buff[i]);     						   IICWaitAck(bus); }		    	   IICStop(bus);delay_us(1);return 0;
} unsigned char IIC_Read_One_Byte(iic_bus_t *bus, uint8_t daddr,uint8_t reg)
{unsigned char dat;IICStart(bus);IICSendByte(bus,daddr<<1);IICWaitAck(bus);IICSendByte(bus,reg);IICWaitAck(bus);IICStart(bus);IICSendByte(bus,(daddr<<1)+1);IICWaitAck(bus);dat = IICReceiveByte(bus);IICSendNotAck(bus);IICStop(bus);return dat;
}uint8_t IIC_Read_Multi_Byte(iic_bus_t *bus, uint8_t daddr, uint8_t reg, uint8_t length, uint8_t buff[])
{unsigned char i;IICStart(bus);IICSendByte(bus,daddr<<1);if(IICWaitAck(bus)){IICStop(bus);		 return 1;		}IICSendByte(bus,reg);IICWaitAck(bus);IICStart(bus);IICSendByte(bus,(daddr<<1)+1);IICWaitAck(bus);for(i=0;i<length;i++){buff[i] = IICReceiveByte(bus);if(i<length-1){IICSendAck(bus);}}IICSendNotAck(bus);IICStop(bus);return 0;
}//
void IICInit(iic_bus_t *bus)
{GPIO_InitTypeDef GPIO_InitStructure = {0};//bus->CLK_ENABLE();GPIO_InitStructure.Pin = bus->IIC_SDA_PIN ;GPIO_InitStructure.Mode = GPIO_MODE_OUTPUT_PP;GPIO_InitStructure.Pull = GPIO_PULLUP;GPIO_InitStructure.Speed = GPIO_SPEED_FREQ_HIGH;HAL_GPIO_Init(bus->IIC_SDA_PORT, &GPIO_InitStructure);GPIO_InitStructure.Pin = bus->IIC_SCL_PIN ;HAL_GPIO_Init(bus->IIC_SCL_PORT, &GPIO_InitStructure);
}

屏幕驱动部分

CST816.h

#ifndef __CST816_H
#define __CST816_H#include "stdint.h"
#include "iic_hal.h"
#include "delay.h"/* CST816 dev pin defination */#define TOUCH_RST_PIN GPIO_PIN_11
#define TOUCH_INT_PIN GPIO_PIN_12
#define TOUCH_RST_PORT GPIOB
#define TOUCH_INT_PORT GPIOB/* functions define */
#define TOUCH_RST_0 HAL_GPIO_WritePin(TOUCH_RST_PORT, TOUCH_RST_PIN, GPIO_PIN_RESET)
#define TOUCH_RST_1 HAL_GPIO_WritePin(TOUCH_RST_PORT, TOUCH_RST_PIN, GPIO_PIN_SET)/* 设备地址 */
#define Device_Addr 	0x15/* 触摸屏寄存器 */
#define GestureID 			0x01
#define FingerNum 			0x02
#define XposH 					0x03
#define XposL 					0x04
#define YposH 					0x05
#define YposL 					0x06
#define ChipID 					0xA7
#define SleepMode				0xE5
#define MotionMask 			0xEC
#define IrqPluseWidth 	0xED
#define NorScanPer 			0xEE
#define MotionSlAngle 	0xEF
#define LpAutoWakeTime 	0xF4
#define LpScanTH 				0xF5
#define LpScanWin 			0xF6
#define LpScanFreq 			0xF7
#define LpScanIdac 			0xF8
#define AutoSleepTime 	0xF9
#define IrqCtl 					0xFA
#define AutoReset 			0xFB
#define LongPressTime 	0xFC
#define IOCtl 					0xFD
#define DisAutoSleep 		0xFE/* 触摸屏坐标结构体 */
typedef struct
{unsigned int X_Pos;unsigned int Y_Pos;
} CST816_Info;extern CST816_Info CST816_Instance;
/* 手势ID识别选项 */
typedef enum
{NOGESTURE = 	0x00,DOWNGLIDE = 	0x01,UPGLIDE = 		0x02,LEFTGLIDE = 	0x03,RIGHTGLIDE = 	0x04,CLICK = 			0x05,DOUBLECLICK = 0x0B,LONGPRESS = 	0x0C,
} GestureID_TypeDef;/* 连续动作配置选项 */
typedef enum
{M_DISABLE = 	0x00,EnConLR = 		0x01,EnConUD = 		0x02,EnDClick = 		0x03,M_ALLENABLE = 0x07,
} MotionMask_TypeDef;/* 中断低脉冲发射方式选项 */
typedef enum
{OnceWLP = 		0x00,EnMotion = 		0x10,EnChange = 		0x20,EnTouch = 		0x40,EnTest = 			0x80,
} IrqCtl_TypeDef;/* 触摸屏初始化相关函数 */
void CST816_GPIO_Init(void);
void CST816_RESET(void);
void CST816_Init(void);/* 触摸屏操作函数 */
void CST816_Get_XY_AXIS(void);
uint8_t CST816_Get_ChipID(void);
uint8_t CST816_Get_FingerNum(void);
/* 触摸屏读写函数 */
void CST816_IIC_WriteREG(uint8_t addr, uint8_t dat);
uint8_t CST816_IIC_ReadREG(unsigned char addr);/* 触摸屏有关参数配置函数 */
void CST816_Config_MotionMask(uint8_t mode);
void CST816_Config_AutoSleepTime(uint8_t time);
void CST816_Config_MotionSlAngle(uint8_t x_right_y_up_angle);
void CST816_Config_NorScanPer(uint8_t Period);
void CST816_Config_IrqPluseWidth(uint8_t Width);
void CST816_Config_LpScanTH(uint8_t TH);
void CST816_Wakeup(void);
void CST816_Sleep(void);#endif

CST816.c

#include "CST816.h" #define TOUCH_OFFSET_Y 15CST816_Info	CST816_Instance;iic_bus_t CST816_dev =
{.IIC_SDA_PORT = GPIOB,.IIC_SCL_PORT = GPIOB,.IIC_SDA_PIN = GPIO_PIN_9,.IIC_SCL_PIN = GPIO_PIN_8,
};/*
*********************************************************************************************************
*	函 数 名: CST816_GPIO_Init
*	功能说明: CST816 GPIO口初始化
*	形    参:none
*	返 回 值: none
*********************************************************************************************************
*/
void CST816_GPIO_Init(void)
{	GPIO_InitTypeDef GPIO_InitStructure = {0};__HAL_RCC_GPIOB_CLK_ENABLE();__HAL_RCC_GPIOA_CLK_ENABLE();/* 初始化复位引脚 */GPIO_InitStructure.Pin = TOUCH_RST_PIN;GPIO_InitStructure.Mode = GPIO_MODE_OUTPUT_PP;GPIO_InitStructure.Pull = GPIO_PULLUP;GPIO_InitStructure.Speed = GPIO_SPEED_FREQ_VERY_HIGH;HAL_GPIO_Init(TOUCH_RST_PORT, &GPIO_InitStructure);HAL_GPIO_WritePin(TOUCH_RST_PORT,TOUCH_RST_PIN,GPIO_PIN_SET);/* 初始化中断引脚,不用中断的话屏蔽掉 *//* 初始化I2C引脚 */IICInit(&CST816_dev);/* 给一个停止信号, 复位I2C总线上的所有设备到待机模式 *///IICStop(&CST816_dev);
}/*
*********************************************************************************************************
*	函 数 名: CST816_Init
*	功能说明: CST816初始化
*	形    参:none
*	返 回 值: none
*********************************************************************************************************
*/
void CST816_Init(void)
{CST816_GPIO_Init();CST816_Config_AutoSleepTime(5);
}/*
*********************************************************************************************************
*	函 数 名: CST816_IIC_ReadREG
*	功能说明: 读取触摸屏单个寄存器的数据
*	形    参:reg:寄存器地址
*	返 回 值: 返回寄存器存储的数据
*********************************************************************************************************
*/
uint8_t CST816_IIC_ReadREG(uint8_t addr)
{return IIC_Read_One_Byte(&CST816_dev,Device_Addr,addr);
}/*
*********************************************************************************************************
*	函 数 名: CST816_IIC_WriteREG
*	功能说明: 向触摸屏的寄存器写入数据
*	形    参:addr:寄存器地址
*						dat:	写入的数据
*	返 回 值: 返回寄存器存储的数据
*********************************************************************************************************
*/
void CST816_IIC_WriteREG(uint8_t addr, uint8_t dat)
{IIC_Write_One_Byte(&CST816_dev,Device_Addr,addr,dat);
}/*
*********************************************************************************************************
*	函 数 名: TOUCH_RESET
*	功能说明: 触摸屏复位
*	形    参:无
*	返 回 值: 无
*********************************************************************************************************
*/
void CST816_RESET(void)
{TOUCH_RST_0;HAL_Delay(10);TOUCH_RST_1;HAL_Delay(100);
}/*
*********************************************************************************************************
*	函 数 名: TOUCH_READ_X
*	功能说明: 读取触摸屏在触摸时的坐标值
*	形    参:无
*	返 回 值: 无 (数据存储在CST816_Instance结构体中)
*********************************************************************************************************
*/
void CST816_Get_XY_AXIS(void)
{uint8_t DAT[4];IIC_Read_Multi_Byte(&CST816_dev,Device_Addr,XposH,4,DAT);CST816_Instance.X_Pos=((DAT[0]&0x0F)<<8)|DAT[1];//(temp[0]&0X0F)<<4|CST816_Instance.Y_Pos=((DAT[2]&0x0F)<<8)|DAT[3] + TOUCH_OFFSET_Y;//(temp[2]&0X0F)<<4|
}/*
*********************************************************************************************************
*	函 数 名: CST816_Get_FingerNum
*	功能说明: 读取触摸屏的手指触摸个数,0xFF为睡眠
*	形    参:无
*	返 回 值: 返回芯片ID
*********************************************************************************************************
*/
uint8_t CST816_Get_FingerNum(void)
{return CST816_IIC_ReadREG(FingerNum);
}/*
*********************************************************************************************************
*	函 数 名: CST816_Get_ChipID
*	功能说明: 读取触摸屏的芯片ID
*	形    参:无
*	返 回 值: 返回芯片ID
*********************************************************************************************************
*/
uint8_t CST816_Get_ChipID(void)
{return CST816_IIC_ReadREG(ChipID);
}/*
*********************************************************************************************************
*	函 数 名: CST816_Config_MotionMask
*	功能说明: 使能连续动作(连续左右滑动,连续上下滑动,双击)
*	形    参:mode:模式(5种)
*	返 回 值: 无
*	注    意:使能连续动作会增加响应时间
*********************************************************************************************************
*/
void CST816_Config_MotionMask(uint8_t mode)
{CST816_IIC_WriteREG(MotionMask,mode);
}/*
*********************************************************************************************************
*	函 数 名: CST816_Config_AutoSleepTime
*	功能说明: 规定time内无触摸,自动进入低功耗模式
*	形    参:time:时间(s)
*	返 回 值: 无
*********************************************************************************************************
*/
void CST816_Config_AutoSleepTime(uint8_t time)
{CST816_IIC_WriteREG(AutoSleepTime,time);
}/*
*********************************************************************************************************
*	函 数 名: CST816_Sleep
*	功能说明: 进入睡眠,无触摸唤醒功能
*	形    参:无
*	返 回 值: 无
*********************************************************************************************************
*/
void CST816_Sleep(void)
{CST816_IIC_WriteREG(SleepMode,0x03);
}/*
*********************************************************************************************************
*	函 数 名: CST816_Wakeup
*	功能说明: 唤醒
*	形    参:无
*	返 回 值: 无
*********************************************************************************************************
*/
void CST816_Wakeup(void)
{CST816_RESET();
}/*
*********************************************************************************************************
*	函 数 名: CST816_Config_MotionSlAngle
*	功能说明: 手势检测滑动分区角度控制。Angle=tan(c)*10 c为以x轴正方向为基准的角度。
*	形    参:x_right_y_up_angle:角度值
*	返 回 值: 无
*********************************************************************************************************
*/
void CST816_Config_MotionSlAngle(uint8_t x_right_y_up_angle)
{CST816_IIC_WriteREG(MotionSlAngle,x_right_y_up_angle);
}/*
*********************************************************************************************************
*	函 数 名: CST816_Config_NorScanPer
*	功能说明: 正常快速检测周期配置函数。
*						此值会影响到LpAutoWakeTime和AutoSleepTime。 
*						单位10ms,可选值:1~30。默认值为1。
*	形    参:Period:周期值
*	返 回 值: 无
*********************************************************************************************************
*/
void CST816_Config_NorScanPer(uint8_t Period)
{if(Period >= 30)Period = 30;CST816_IIC_WriteREG(NorScanPer,Period);
}/*
*********************************************************************************************************
*	函 数 名: CST816_Config_IrqPluseWidth
*	功能说明: 中断低脉冲输出宽度配置函数
*	形    参:Period:周期值
*	返 回 值: 无
*********************************************************************************************************
*/
void CST816_Config_IrqPluseWidth(uint8_t Width)
{if(Width >= 200)Width = 200;CST816_IIC_WriteREG(IrqPluseWidth,Width);
}/*
*********************************************************************************************************
*	函 数 名: CST816_Config_NorScanPer
*	功能说明: 低功耗扫描唤醒门限配置函数。越小越灵敏。默认值48
*	形    参:TH:门限值
*	返 回 值: 无
*********************************************************************************************************
*/
void CST816_Config_LpScanTH(uint8_t TH)
{CST816_IIC_WriteREG(LpScanTH,TH);
}
3.sys

delay.h

#ifndef _DELAY_H
#define _DELAY_H
#include "sys.h"	  void delay_init(void);
void delay_ms(u16 nms);
void delay_us(u32 nus);
#endif

delay.c

#include "delay.h"
#include "sys.h"/* 
//roughly delay
void delay_us(u32 nus)
{		u32 i;u16 temp;temp = nus*SYS_CLK/15;for(i=0;i<temp;i++);
}//延时nms
//nms:要延时的ms数
void delay_ms(u16 nms)
{u32 i;for(i=0;i<nms;i++) delay_us(1000);
}
*/void delay_init(void)
{HAL_SYSTICK_CLKSourceConfig(SYSTICK_CLKSOURCE_HCLK);/* Configure the SysTick to have interrupt in 1ms time basis*/HAL_SYSTICK_Config(SystemCoreClock / (1000U / uwTickFreq));
}#if OS_SUPPORT 						    								   
void delay_us(u32 nus)
{		u32 ticks;u32 told,tnow,tcnt=0;u32 reload=SysTick->LOAD;				   	 ticks=nus*SYS_CLK; 						 delay_osschedlock();					told=SysTick->VAL;        				while(1){tnow=SysTick->VAL;	if(tnow!=told){	    if(tnow<told)tcnt+=told-tnow;//这里注意一下SYSTICK是一个递减的计数器就可以了.	else tcnt+=reload-tnow+told;	    told=tnow;if(tcnt>=ticks)break;			}  };delay_osschedunlock();															    
}  void delay_ms(u16 nms)
{	if(delay_osrunning&&delay_osintnesting==0)    {		 if(nms>=fac_ms)						{ delay_ostimedly(nms/fac_ms);	}nms%=fac_ms;						 }delay_us((u32)(nms*1000));			
}
#else  void delay_us(u32 nus)
{		u32 ticks;u32 told,tnow,tcnt=0;u32 reload=SysTick->LOAD;				    	 ticks=nus*SYS_CLK; 						told=SysTick->VAL;        				while(1){tnow=SysTick->VAL;	if(tnow!=told){	    if(tnow<told)tcnt+=told-tnow;	else tcnt+=reload-tnow+told;	    told=tnow;if(tcnt>=ticks)break;			}  }
}void delay_ms(u16 nms)
{u32 i;for(i=0;i<nms;i++) delay_us(1000);
}
#endif

sys.h

#ifndef __SYS_H__
#define __SYS_H__#include "stm32f4xx.h"
#include "stm32f4xx_hal.h"#define OS_SUPPORT 	0
#define SYS_CLK 		100typedef int32_t  s32;
typedef int16_t s16;
typedef int8_t  s8;typedef const int32_t sc32;  
typedef const int16_t sc16;  
typedef const int8_t sc8;  typedef __IO int32_t  vs32;
typedef __IO int16_t  vs16;
typedef __IO int8_t   vs8;typedef __I int32_t vsc32;  
typedef __I int16_t vsc16; 
typedef __I int8_t vsc8;   typedef uint32_t  u32;
typedef uint16_t u16;
typedef uint8_t  u8;typedef const uint32_t uc32;  
typedef const uint16_t uc16;  
typedef const uint8_t uc8; typedef __IO uint32_t  vu32;
typedef __IO uint16_t vu16;
typedef __IO uint8_t  vu8;typedef __I uint32_t vuc32;  
typedef __I uint16_t vuc16; 
typedef __I uint8_t vuc8; #endif
4.字体、图片

图片pic.h

#ifndef _PIC_H
#define _PIC_H
//中间添加所用到的图片#endif

字体lcdfont.h

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hjln.cn/news/46828.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈,一经查实,立即删除!

相关文章

硬件开发笔记(十九):Altium Designer 21软件介绍和安装过程

前言AD硬件设计软件之一,前面说了allego,但是allego对项目的管理、原理图生成PCB,PCB反向原理图等方面比较复杂,对于一般的硬件(非多个高速电路),选择AD能够加大的节省开发工作量。  本篇介绍AD21、AD21较20新增的高效功能和其安装过程。 Altium Designer 21简介Altiu…

卡特兰数关于凸多边形的证明

将这个凸多边形编号,如下对于任意一种划分,边\((1,n)\)一定属于且只属于一个三角形,考虑这个三角形的另一个顶点为\(k\),于是有递推公式: \[f_n=\sum_{i=2}^{n-1}f_i\times f_{n-i+1} \]可知为卡特兰数

linux内存管理(十)- 页面回收(二)

本篇了解一下内核是怎样触发页面回收的。 触发内存回收的方式有两种,同步和异步回收。alloc_pages在分配内存的时候,如果内存短缺会主动回收内存,这是同步回收;内核有一个或多个kswapd内核线程负责在后台回收内存,这是异步。看一下shrink_active_liststatic void shrink_l…

Windows CSC提权漏洞复现(CVE-2024-26229)

漏洞信息 Windows CSC服务特权提升漏洞。 当程序向缓冲区写入的数据超出其处理能力时,就会发生基于堆的缓冲区溢出,从而导致多余的数据溢出到相邻的内存区域。这种溢出会损坏内存,并可能使攻击者能够执行任意代码或未经授权访问系统。本质上,攻击者可以编写触发溢出的恶意代…

【日记】忽然想买根卷发棒了……(622 字)

正文突然想买一根卷发棒了,虽然还没有多长,但刘海全搭在前面不太好看。忽然有些理解女孩子们的心情了。说起头发,晚上练头定下落接三角撑,终于找到了感觉。不过因为头要往前滑,刚开始在垫子上找感觉,那个垫子又糙,滑的时候感觉头发被拉得生疼。不过头发长度好歹能让小猫…

linux 配置java环境变量

1.下载与安装 查看操作系统位数 uname -m 如果输出是x86_64,那么你的系统是64位的; 如果输出是i686或i386,那么你的系统是32位的。openJDK下载地址:清华大学开源软件镜像站 以jdk11为例,下载地址为:https://mirror.tuna.tsinghua.edu.cn/Adoptium/11/jdk/x64/linux/OpenJ…

使用.NET Core创建Windows服务

一、 使用VS创建 打开Visual Studio,创建新项目,找到Worker Service模板。 二、项目结构说明 创建出来的项目,包含两个主要文件: 1)其中Program.cs文件是应用的启动“引导程序”; 2)另外一个文件是worker.cs文件,在这个文件中,可以编写自己的服务逻辑。 三、将应用转换…