先上效果
VID_20240629_191036
VID_20240701_195036
使用100mhz的SPI频率,在不使用DMA情况下,大约10帧左右,加上DMA后提高到接近40帧.
使用480*320*2大小的缓冲区,如果单纯刷屏可以减小到HAL库SPI发送函数最大长度.因为缓冲区过大所以分几次发送的.
CUBEMX生成代码
一共需要使用3个外设,定时器可以不用
硬件I2C+SPI+串口

首先使能RCC,SPI,USART,I2C
电容触摸
电容触摸芯片GT911,I2C频率最大400khz,STM32开到1000k也无所谓,没有使能DMA和中断,使用外部中断获取触摸信号,读寄存器

对配置好的I2C封装一下,这里沿用了以前的代码,因为GT911有16位寄存器,所以再写一个16位读写函数.
void i2c_write(uint8_t devaddr,uint8_t addr,uint8_t pdata,int len){
HAL_I2C_Mem_Write(&I2C,devaddr,addr,I2C_MEMADD_SIZE_8BIT,&pdata,len,1000);
}
uint8_t i2c_read(uint8_t devaddr,uint8_t addr)
{ uint8_t data;
HAL_I2C_Mem_Read(&I2C,devaddr,addr,I2C_MEMADD_SIZE_8BIT,&data,1,1000);
return data;
}
void i2c_write16(uint8_t devaddr,uint16_t addr,uint8_t pdata,int len){
HAL_I2C_Mem_Write(&I2C,devaddr,addr,I2C_MEMADD_SIZE_16BIT,&pdata,len,1000);
}
uint8_t i2c_read16(uint8_t devaddr,uint16_t addr)
{ uint8_t data;
HAL_I2C_Mem_Read(&I2C,devaddr,addr,I2C_MEMADD_SIZE_16BIT,&data,1,1000);
return data;
}
void i2c_read16n(uint8_t devaddr,uint16_t addr,uint8_t* data,uint8_t n)
{
HAL_I2C_Mem_Read(&I2C,devaddr,addr,I2C_MEMADD_SIZE_16BIT,data,n,1000);
}
void i2c_write16n(uint8_t devaddr,uint16_t addr,uint8_t* data,uint8_t n)
{
HAL_I2C_Mem_Write(&I2C,devaddr,addr,I2C_MEMADD_SIZE_16BIT,data,n,1000);
}
GT911初始化
GT911的寄存器表大概就用这几个就好了
#define USE_GT911
#define hi2cx GT911
//#define GT_WRITECFG //写配置表
#define GT_ADDR 0X28
#define GT_CTRL_REG 0X8040 //GT911控制寄存器
#define GT_CFGS_REG 0X8047 //GT911配置起始地址寄存器
#define GT_CHECK_REG 0X80FF //GT911校验和寄存器
#define GT_PID_REG 0X8140 //GT911产品ID寄存器
#define GT_GSTID_REG 0X814E //GT911当前检测到的触摸情况
GT911的初始化很简单,不用配置什么,上电就能读取数据,因为我没找到芯片id到底是多少所以没有读id,同时千万别写控制寄存器0x8040,写了就裂开,找厂家要配置表.这里选择了要不要写配置表
void GT911_INIT(){
HAL_Delay(100);
uint8_t data;
#ifdef GT_WRITECFG
i2c_write16(GT_ADDR,GT_CTRL_REG,2,1);
i2c_write16n(GT_ADDR,0x8047,(uint8_t *)datacfg,186);
i2c_write16(GT_ADDR,GT_CTRL_REG,0,1);
#endif
touch=0;
HAL_Delay(100);
i2c_write16(GT_ADDR,GT_GSTID_REG,0x00,1);
}
随后就是判断是否被触摸以及触摸点数.
通过电容触摸屏GT911、GT928、GT9147的使用_gt911 3.5寸配置文件-优快云博客得知,当触摸发生时,寄存器0x814E 最高位变成1,同时低四位表示有几个点
例如10000011:触摸按下,有3个点按下,这里我用了两次判断,先判断高位在判断低四位是否不为0,因为触摸结束的时候没有及时清除814E寄存器,第8位还为1,会误入读取坐标,加一个判断能够在触摸结束马上得知.
通过上文得知,坐标寄存器都是挨着的,只用按顺序读就好了氛围高8位和低8位
坐标=高八位*255+低八位
读完以后存储到LIST里面,方便读取.

void GET_NUM(void){
#ifdef TOUCHOK
touch=0;
uint8_t data;
data=i2c_read16(GT_ADDR,GT_GSTID_REG);
if((data&0x80)!=0){
if((data&0X0f)!=0){
touch=data&0x0F;
read_point(LIST,touch);
}
i2c_write16(GT_ADDR,GT_GSTID_REG,0x00,1);
}
return ;
#endif
printf("TOUCH ERROR PLEASE TRY LATER\r\n");
}
void read_point(POINT LIST[],uint8_t NUM){
uint16_t x,y;
i2c_read16n(GT_ADDR,0x8150,datatemp,8*NUM);
for(uint8_t i=0;i<NUM;i++){
x=(datatemp[i*8]+(datatemp[i*8+1]<<8));
y=(datatemp[i*8+2]+(datatemp[i*8+3]<<8));
LIST[i].xPos=x;
LIST[i].yPos=y;
LIST[i].id=i+1;
printf("TOUCH %d X->%d Y->%d\r\n",i+1,x,y);
}
}
测试,数据也是比较准的

SPI初始化
200mhz 2分频 ,h7就是暴力,直接硬干都有10多帧,8位传输,仅发送,加入DMA,开启SPI DMA中断


其他配置都差不多不用改
封装一下发送函数
void SPI_ReadWriteByte(uint8_t TxData)
{
HAL_SPI_Transmit(&SPI,&TxData,1,10); //·µ»ØÊÕµ½µÄÊý¾Ý
}
void SPI_SetSpeed(uint32_t SPI_BaudRatePrescaler)
{
assert_param(IS_SPI_BAUDRATE_PRESCALER(SPI_BaudRatePrescaler));//ÅжÏÓÐЧÐÔ
__HAL_SPI_DISABLE(&SPI); //¹Ø±ÕSPI
SPI.Instance->CFG1&=~(0X7<<28); //λ30-28ÇåÁ㣬ÓÃÀ´ÉèÖò¨ÌØÂÊ
SPI.Instance->CFG1|=SPI_BaudRatePrescaler;//ÉèÖÃSPIËÙ¶È
__HAL_SPI_ENABLE(&SPI); //ʹÄÜSPI
}
引脚,这里使用cubemx的宏定义,方便移植,命名好就能直接使用

DMA
这里是最难绷的,前前后后试了好久,不知道为什么一直发送不成功,返回不是HAL_ERROR就是HAL_BUSY,直到这几天突然看到片文章STM32H7:解决DMA传输无效的问题-优快云博客
牛莫得,H7默认的程序执行范围起始位置DMA是无法访问的,解决方法也很简单

将起始区域修改为可以的就好了
LCD代码
这里使用了安富莱的LCD代码
lcd.h注释不知道为什么乱码,内容挺好理解的
#ifndef __LCD_H
#define __LCD_H
#include "stdlib.h"
#include "GPIO.h"
typedef signed char int8_t;
typedef signed short int int16_t;
typedef signed int int32_t;
typedef signed long long int64_t;
typedef unsigned char uint8_t;
typedef unsigned short int uint16_t;
typedef unsigned int uint32_t;
typedef unsigned long long uint64_t;
typedef uint32_t u32;
typedef uint16_t u16;
typedef uint8_t u8;
extern uint16_t D_Color;
extern uint16_t B_Color;
/******************************************************************************
½Ó¿Ú¶¨Ò壬Çë¸ù¾Ý½ÓÏßÐ޸IJ¢ÐÞ¸ÄÏàÓ¦IO³õʼ»¯--Çý¶¯°å×ÓºÍIOÒª¶ÔÓ¦
// #define LCD_SDA //PD7 //Êý¾ÝÊäÈëÏß
// #define LCD_SCL //PB3 //ʱÖÓÏß
// #define LCD_CS //PB4 //Ƭѡ
// #define LCD_RESET //PG11 //Êý¾ÝÊä³ö/¸´Î»
// #define LCD_RS //PD6 //ÃüÁî/Êý¾ÝÇл»
// #define LCD_BLK //PG14 //±³¹â¿ØÖÆ
*******************************************************************************/
//Òº¾§¿ØÖÆ¿ÚÖÃ1²Ù×÷Óï¾äºê¶¨Òå
#define LCD_SDA_SET HAL_GPIO_WritePin(LCD_MOSI_GPIO_Port,LCD_MOSI_Pin,GPIO_PIN_SET) //PB15ÖÃ1 LCD_SDI£º PB15 //Êý¾ÝÊäÈëÏß
#define LCD_SCL_SET HAL_GPIO_WritePin(LCD_CLK_GPIO_Port,LCD_CLK_Pin,GPIO_PIN_SET) //PB13ÖÃ1 LCD_SCL£º PB13 //ʱÖÓÏß
#define LCD_CS_SET HAL_GPIO_WritePin(LCD_CS_GPIO_Port,LCD_CS_Pin,GPIO_PIN_SET) //PB12ÖÃ1 LCD_CS£º PB12 //Ƭѡ
#define LCD_RST_SET HAL_GPIO_WritePin(LCD_RESET_GPIO_Port,LCD_RESET_Pin,GPIO_PIN_SET) //PB14ÖÃ1 LCD_SDO £ºPB14 //Êý¾ÝÊä³ö/¸´Î»
#define LCD_RS_SET HAL_GPIO_WritePin(LCD_RS_GPIO_Port,LCD_RS_Pin,GPIO_PIN_SET) //PB1ÖÃ1 LCD_RS£º PB1 //ÃüÁî/Êý¾ÝÇл»
#define LCD_BLK_SET HAL_GPIO_WritePin(LCD_BL_GPIO_Port,LCD_BL_Pin,GPIO_PIN_SET) //PB0ÖÃ1 LCD_BLK £ºPB0 //±³¹â¿ØÖÆ
//Òº¾§¿ØÖÆ¿ÚÖÃ0²Ù×÷Óï¾äºê¶¨Òå
#define LCD_SDA_CLR HAL_GPIO_WritePin(LCD_MOSI_GPIO_Port,LCD_MOSI_Pin,GPIO_PIN_RESET) //PB15ÖÃ0 //DIN LCD_SDI£º PB15 //Êý¾ÝÊäÈëÏß
#define LCD_SCL_CLR HAL_GPIO_WritePin(LCD_SCL_GPIO_Port,LCD_CLK_Pin,GPIO_PIN_RESET) //PB13ÖÃ0 //CLK LCD_SCL£º PB13 //ʱÖÓÏß
#define LCD_CS_CLR HAL_GPIO_WritePin(LCD_CS_GPIO_Port,LCD_CS_Pin,GPIO_PIN_RESET) //PB12ÖÃ0/CS LCD_CS£º PB12 //Ƭѡ
#define LCD_RST_CLR HAL_GPIO_WritePin(LCD_RESET_GPIO_Port,LCD_RESET_Pin,GPIO_PIN_RESET) //PB14ÖÃ0 //RES LCD_SDO £ºPB14 //Êý¾ÝÊä³ö/¸´Î»
#define LCD_RS_CLR HAL_GPIO_WritePin(LCD_RS_GPIO_Port,LCD_RS_Pin,GPIO_PIN_RESET) //PB1ÖÃ0 //DC LCD_RS£º PB1 //ÃüÁî/Êý¾ÝÇл»
#define LCD_BLK_CLR HAL_GPIO_WritePin(LCD_BL_GPIO_Port,LCD_BL_Pin,GPIO_PIN_RESET) //PB0ÖÃ0 //DIN LCD_BLK £ºPB0 //±³¹â¿ØÖÆ
#define LCD_BLK_On LCD_BLK_SET //¿ª±³¹â LCD±³¹â¿ØÖÆ
#define LCD_BLK_Off LCD_BLK_CLR //¹Ø±³¹â LCD±³¹â¿ØÖÆ
//LCDÖØÒª²ÎÊý¼¯
typedef struct
{
u16 width; //LCD ¿í¶È
u16 height; //LCD ¸ß¶È
u16 id; //LCD ID
u8 dir; //ºáÆÁ»¹ÊÇÊúÆÁ¿ØÖÆ£ºÊúÆÁºÍºáÆÁ¡£
u16 wramcmd; //¿ªÊ¼Ð´gramÖ¸Áî
u16 setxcmd; //ÉèÖÃx×ø±êÖ¸Áî
u16 setycmd; //ÉèÖÃy×ø±êÖ¸Áî
}_lcd_dev;
/////////////////////////////////////Óû§ÅäÖÃÇø///////////////////////////////////
//Ö§³ÖºáÊúÆÁ¿ìËÙ¶¨ÒåÇл»
#define LCD_DIR_Mode 0 //4ÖÖ¹¤×÷ģʽ£¬0ºÍ2ÊÇÊúÆÁģʽ£¬1ºÍ3ÊǺáÆÁģʽ
#define USE_HORIZONTAL 0 //·½ÏòÉèÖ㺠0,ÊúÆÁģʽ 1,ºáÆÁģʽ.
//////////////////////////////////////////////////////////////////////////////////
//LCD²ÎÊý
extern _lcd_dev lcddev; //¹ÜÀíLCDÖØÒª²ÎÊý
//LCDµÄ»±ÊÑÕÉ«ºÍ±³¾°É«
extern u16 POINT_COLOR;//ĬÈϺìÉ«
extern u16 BACK_COLOR; //±³¾°ÑÕÉ«.ĬÈÏΪ°×É«
#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 //»ÒÉ«
//GUIÑÕÉ«
#define DARKBLUE 0x01CF //ÉîÀ¶É«
#define LIGHTBLUE 0x7D7C //dzÀ¶É«
#define GRAYBLUE 0x5458 //»ÒÀ¶É«
//ÒÔÉÏÈýɫΪPANELµÄÑÕÉ«
#define LIGHTGREEN 0x841F //dzÂÌÉ«
#define LGRAY 0xC618 //dz»ÒÉ«(PANNEL),´°Ìå±³¾°É«
#define GRAY0 0xEF7D //»ÒÉ«0
#define GRAY1 0x8410 //»ÒÉ«1
#define GRAY2 0x4208 //»ÒÉ«2
#define LGRAYBLUE 0xA651 //dz»ÒÀ¶É«(Öмä²ãÑÕÉ«)
#define LBBLUE 0x2B12 //Ç³×ØÀ¶É«(Ñ¡ÔñÌõÄ¿µÄ·´É«)
#define LCD_Delay_us delay_us //ÑÓʱº¯Êý
#define LCD_HAL_Delay HAL_Delay //ÑÓʱº¯Êý
////////////////////////Ó²¼þÇý¶¯-¹¦Äܺ¯Êý//////DevEBox ´óÔ½´´ÐÂ//////shop389957290.taobao.com///////////////////////////////////////////////////
void LCD_GPIO_Init(void); //Òº¾§IO³õʼ»¯ÅäÖÃ
void LCD_WR_REG(uint16_t regval); //Òº¾§ÆÁ--д¼Ä´æÆ÷º¯Êý
void LCD_WR_DATA8(u8 data); //д8λÊý¾Ý
void LCD_WR_DATA16(uint16_t data); //д16λÊý¾Ý
void LCD_Init(void); //³õʼ»¯
void LCD_HardwareRest(void); //Ó²¸´Î»--Èç¹ûIOÁ¬½Ó£¬Ó²¼þ¸´Î»¿É¿ØÓÐЧ
void LCD_SoftRest(void); //Èí¸´Î»
void LCD_DisplayOn(void); //¿ªÏÔʾ
void LCD_DisplayOff(void); //¹ØÏÔʾ
//////////////////ÒÔϺ¯ÊýÊÇÆÁÄ»ÏÔʾͼÐεļòµ¥Çý¶¯º¯Êý////////////DevEBox ´óÔ½´´ÐÂ//////shop389957290.taobao.com//////////////////////////////////////
void LCD_SetCursor(u16 Xpos, u16 Ypos); //ÉèÖùâ±ê
void LCD_DrawPoint(u16 x,u16 y); //»µã--ʹÓÃÉèÖõıʼâÑÕÉ«
void LCD_Fast_DrawPoint(u16 x,u16 y,u16 color); //¿ìËÙ»µã--ʹÓõ±Ç°ÊäÈëÑÕÉ«²ÎÊý
void LCD_QCLEAR_DMA(u16 color);
void LCD_QCLEAR(u16 color);
void LCD_Clear(u16 color);
void LCD_Draw_Circle(u16 x0,u16 y0,u8 r, 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 LCD_Fill(u16 sx,u16 sy,u16 ex,u16 ey,u16 color); //Ìî³äµ¥É«
void LCD_Color_Fill(u16 sx,u16 sy,u16 ex,u16 ey,u16 *color); //Ìî³äÖ¸¶¨ÑÕÉ«
void LCD_ShowChar(u16 x,u16 y,u8 num,u8 size,u16 color,u8 mode); //ÏÔʾһ¸ö×Ö·û
void LCD_ShowNum(u16 x,u16 y,u32 num,u8 len,u8 size,u16 color); //ÏÔʾһ¸öÊý×Ö
void LCD_ShowxNum(u16 x,u16 y,u32 num,u8 len,u8 size,u16 color,u8 mode); //ÏÔʾ Êý×Ö
void LCD_ShowString(u16 x,u16 y,u16 width,u16 height,u8 size,u16 color,u8 *p,u8 mode); //ÏÔʾһ¸ö×Ö·û´®,12/16×ÖÌå
void LCD_WriteReg(u16 LCD_Reg, u16 LCD_RegValue); //д¼Ä´æÆ÷
void LCD_WriteRAM_Prepare(void); //¿ªÊ¼Ð´GRAM ÃüÁî
void LCD_WriteRAM(u16 RGB_Code); //LCDдGRAM
void LCD_Scan_Dir(u8 dir); //ÉèÖÃÆÁɨÃè·½Ïò
void LCD_Display_Dir(u8 dir); //ÉèÖÃÆÁÄ»ÏÔʾ·½Ïò
void LCD_Set_Window(u16 sx,u16 sy,u16 width,u16 height); //ÉèÖô°¿Ú
void SHOW_PIC_DMA(void);
void Draw_Test(void);//»æÍ¼¹¤¾ßº¯Êý²âÊÔ
void Color_Test(void);//ÑÕÉ«Ìî³äÏÔʾ²âÊÔ
void Font_Test(void);// ×ÖÌå×ÖÐÎÏÔʾ²âÊÔ
void GBK_LibFont_Test(void);//GBK ×ÖÌå×ÖÐÎÏÔʾ²âÊÔ
void Demo_Menu(void);//ÑÝʾ³ÌÐò²Ëµ¥
#endif
/*******************************************************************************/
//DevEBox ´óÔ½´´ÐÂ
//ÌÔ±¦µêÆÌ£ºmcudev.taobao.com
//ÌÔ±¦µêÆÌ£ºshop389957290.taobao.com
/*******************************************************************************/
lcd.c
#include "lcd.h"
#include "stdlib.h"
#include "font.h"
#include "usart.h"
#include "Text.h"
#include "Dis_Picture.h"
#include "SPI.h"
#include "stdio.h"
#include "Picture.h"
u16 POINT_COLOR=0x0000; //»±ÊÑÕÉ«
u16 BACK_COLOR=0xFFFF; //±³¾°É«
uint8_t gram[320*480*2]={0};
//¹ÜÀíLCDÖØÒª²ÎÊý
//ĬÈÏΪÊúÆÁ
_lcd_dev lcddev;
/******************************************************************************/
void LCD_GPIO_Init(void)
{
__HAL_RCC_GPIOB_CLK_ENABLE();
__HAL_RCC_GPIOC_CLK_ENABLE();
HAL_GPIO_WritePin(GPIOB,LCD_RS_Pin,GPIO_PIN_SET); //PB1ÖÃ1
HAL_GPIO_WritePin(GPIOC,LCD_CS_Pin,GPIO_PIN_SET); //PB12ÖÃ1
HAL_GPIO_WritePin(GPIOC,LCD_RESET_Pin,GPIO_PIN_SET);
MX_SPI1_Init();
//SPI_SetSpeed(SPI_BAUDRATEPRESCALER_8);
}
void LCD_WR_REG(u16 regval)//д¼Ä´æÆ÷
{
LCD_CS_CLR; //LCD_CS=0 //Ƭѡ
LCD_RS_CLR; //LCD_RS=0 //ÉèÖÃÃüÁî״̬
SPI_ReadWriteByte(regval&0x00FF);
LCD_CS_SET; //LCD_CS=1
}
void LCD_WR_DATA8(u8 data) //д8λÊý¾Ý
{
LCD_CS_CLR; //LCD_CS=0 //Ƭѡ
LCD_RS_SET; //LCD_RS=1 //ÉèÖÃÊý¾Ý״̬
SPI_ReadWriteByte(data);
LCD_CS_SET; //LCD_CS=1
}
void LCD_WR_DATA16(u16 data)//д16λÊý¾Ý
{
LCD_CS_CLR; //LCD_CS=0 //Ƭѡ
LCD_RS_SET; //LCD_RS=1 //ÉèÖÃÊý¾Ý״̬
SPI_ReadWriteByte(data>>8);
SPI_ReadWriteByte(data);
LCD_CS_SET; //LCD_CS=1
}
void LCD_WriteReg(u16 LCD_Reg, u16 LCD_RegValue)//дҺ¾§ÆÁ¼Ä´æÆ÷
{
LCD_WR_REG(LCD_Reg); //дÈëҪдµÄ¼Ä´æÆ÷ÐòºÅ
LCD_WR_DATA8(LCD_RegValue);//дÈëÊý¾Ý
}
void LCD_WriteRAM_Prepare(void)//¿ªÊ¼Ð´GRAM
{
LCD_WR_REG(lcddev.wramcmd);
}
void LCD_WriteRAM(u16 RGB_Code)//дµãÑÕÉ«
{
LCD_WR_DATA16(RGB_Code);//дʮÁùλGRAM
}
void LCD_DisplayOn(void)//LCD¿ªÆô
{
LCD_WR_REG(0X29); //¿ªÆôÏÔʾ
}
void LCD_DisplayOff(void)//LCD¿ª¹Ø±Õ
{
LCD_WR_REG(0X28); //¹Ø±ÕÏÔʾ
}
void LCD_SoftRest(void)
{
LCD_WR_REG(0x01); //·¢ËÍÈí¸´Î»ÃüÁî
LCD_HAL_Delay(50); // delay 50 ms
}
void LCD_HardwareRest(void)
{
LCD_RST_CLR; //Òº¾§ÆÁ¸´Î» --Ó²¸´Î»--ʹÄÜ //PB14×÷ΪҺ¾§ÆÁ¸´Î»¿ØÖÆÒý½Å
LCD_HAL_Delay(50); // delay 50 ms
LCD_RST_SET; //Òº¾§ÆÁ¸´Î» --Ó²¸´Î»--ʧÄÜ //PB14×÷ΪҺ¾§ÆÁ¸´Î»¿ØÖÆÒý½Å
LCD_HAL_Delay(30); // delay 30 ms
}
void LCD_SetCursor(u16 Xpos, u16 Ypos)//ÉèÖùâ±êλÖÃ
{
LCD_WR_REG(lcddev.setxcmd);
LCD_WR_DATA16(Xpos);
LCD_WR_REG(lcddev.setycmd);
LCD_WR_DATA16(Ypos);
}
void LCD_DrawPoint(u16 x,u16 y)//»µã
{
LCD_SetCursor(x,y);
LCD_WriteRAM_Prepare();
LCD_WR_DATA16(POINT_COLOR);
}
void LCD_TRANMITE(long num){
long i;
LCD_CS_CLR;
LCD_RS_SET;
if(num%38400==0)
for(i=0;i<num;i+=38400)
HAL_SPI_Transmit(&SPI,&gram[i],38400,10);
else{
for(i=0;i<num-38400;i+=38400)
HAL_SPI_Transmit(&SPI,&gram[i],38400,10);
HAL_SPI_Transmit(&SPI,&gram[i],num%38400,10);
}
LCD_CS_SET;
}
void LCD_QCLEAR_DMA(u16 color){
long i;
uint8_t data;
for(i=0;i<320*480*2;i+=2){
gram[i]=color>>8;
gram[i+1]=color;
}
LCD_SetCursor(0x00,0x00);
LCD_WriteRAM_Prepare();
HAL_StatusTypeDef CALL;
LCD_CS_CLR;
LCD_RS_SET;
for(i=0;i<320*480*2;i+=38400){
HAL_SPI_Transmit_DMA(&SPI,&gram[i],38400);
while(HAL_SPI_GetState(&SPI)!=HAL_SPI_STATE_READY);
}
LCD_CS_SET;
}
void LCD_QCLEAR(u16 color){
long i;
for(i=0;i<320*480*2;i+=2){
gram[i]=color>>8;
gram[i+1]=color;
}
LCD_SetCursor(0x00,0x00);
LCD_WriteRAM_Prepare();
LCD_TRANMITE(320*480*2);
}
void LCD_Fast_DrawPoint(u16 x,u16 y,u16 color)
{
LCD_WR_REG(lcddev.setxcmd);
LCD_WR_DATA16(x);
LCD_WR_REG(lcddev.setycmd);
LCD_WR_DATA16(y);
LCD_WR_REG(lcddev.wramcmd);
LCD_WR_DATA16(color);
}
//*******************************************************************/
//º¯Êý£ºvoid LCD_Scan_Dir(u8 dir)
//º¯Êý¹¦ÄÜ£ºÉèÖÃLCDµÄ×Ô¶¯É¨Ãè·½Ïò
//ÊäÈë²ÎÊý£º
//ĬÈÏÉèÖÃΪL2R_U2D,Èç¹ûÉèÖÃΪÆäËûɨÃ跽ʽ,¿ÉÄܵ¼ÖÂÏÔʾ²»Õý³£.
//dir:0~7,´ú±í8¸ö·½Ïò
//DevEBox ´óÔ½´´ÐÂ
//ÌÔ±¦µêÆÌ£ºmcudev.taobao.com
//ÌÔ±¦µêÆÌ£ºshop389957290.taobao.com
//*******************************************************************/
void LCD_Scan_Dir(u8 dir)
{
u8 regval=0;
//ɨÃè·½Ïò¶¨Òå--ɨÃ跽ʽÓв»Í¬¹æ¸ñ£¬¿ÉÄܶ¨Òå²»×óÓÒºÍÉÏϵIJÎÕÕ·½Ïò²»Í¬£¬×᷽ܽʽ£¬Ö»ÓÐһϰËÖÖ
dir=2;
switch(dir)
{
case 0:
regval|=(0<<7)|(0<<6)|(0<<5);
break;
case 1:
regval|=(0<<7)|(1<<6)|(1<<5);
break;
case 2:
regval|=(0<<7)|(1<<6)|(0<<5)|(1<<3);
break;
case 3:
regval|=(1<<7)|(0<<6)|(1<<5);
break;
}
LCD_WriteReg(0x36,regval);//¸Ä±äɨÃè·½ÏòÃüÁî ---´Ë´¦ÐèÒª²é¿´Êý¾ÝÊֲᣬȷ¶¨RGBÑÕÉ«½»»»Î»µÄÅäÖÃ
}
/**************************************************************************/
//º¯Êý£ºvoid LCD_Display_Dir(u8 dir)
//º¯Êý¹¦ÄÜ£ºÉèÖÃLCDµÄÏÔʾ·½Ïò¼°ÏñËØ²ÎÊý
//ÊäÈë²ÎÊý£º
//ÉèÖÃLCDÏÔʾ·½Ïò
////dir: 0,ÊúÆÁ Õý
// 1,ÊúÆÁ ·´
// 2,ºáÆÁ ×ó
// 3,ºáÆÁ ÓÒ
void LCD_Display_Dir(u8 dir)
{
u8 SCAN_DIR;
if(dir==0) //ÊúÆÁ Õý
{
lcddev.dir=0; //ÊúÆÁ
lcddev.width=320;
lcddev.height=480;
lcddev.wramcmd=0X2C;
lcddev.setxcmd=0X2A;
lcddev.setycmd=0X2B;
SCAN_DIR=0; //Ñ¡ÔñɨÃè·½Ïò
}
else if (dir==1) //ºáÆÁ
{
lcddev.dir=0; //ºáÆÁ
lcddev.width=480;
lcddev.height=320;
lcddev.wramcmd=0X2C;
lcddev.setxcmd=0X2A;
lcddev.setycmd=0X2B;
SCAN_DIR=1; //Ñ¡ÔñɨÃè·½Ïò
}
else if (dir==2) //ÊúÆÁ
{
lcddev.dir=1; //ÊúÆÁ
lcddev.width=320;
lcddev.height=480;
lcddev.wramcmd=0X2C;
lcddev.setxcmd=0X2A;
lcddev.setycmd=0X2B;
SCAN_DIR=2; //Ñ¡ÔñɨÃè·½Ïò
}
else if (dir==3) //ºáÆÁ
{
lcddev.dir=1; //ºáÆÁ
lcddev.width=480;
lcddev.height=320;
lcddev.wramcmd=0X2C;
lcddev.setxcmd=0X2A;
lcddev.setycmd=0X2B;
SCAN_DIR=3; //Ñ¡ÔñɨÃè·½Ïò
}
else //ÉèÖÃĬÈÏΪÊúÆÁ--Õý
{
lcddev.dir=0; //ÊúÆÁ
lcddev.width=320;
lcddev.height=480;
lcddev.wramcmd=0X2C;
lcddev.setxcmd=0X2A;
lcddev.setycmd=0X2B;
SCAN_DIR=0; //Ñ¡ÔñɨÃè·½Ïò
}
//////ÒÔÏÂÉèÖã¬Îª´°¿Ú²ÎÊýÉèÖã¬ÉèÖÃÁËÈ«ÆÁµÄÏÔʾ·¶Î§
LCD_Set_Window(0,0,lcddev.width,lcddev.height);//ÉèÖÃÈ«ÆÁ´°¿Ú
/////ÉèÖÃÆÁÄ»ÏÔʾ--ɨÃè·½Ïò
LCD_Scan_Dir(SCAN_DIR); //ÉèÖÃÆÁÄ»ÏÔʾ--ɨÃè·½Ïò
}
void SHOW_PIC_DMA(void){
long i;
LCD_SetCursor(0x00,0x00);
LCD_WriteRAM_Prepare();
LCD_CS_CLR;
LCD_RS_SET;
for(i=0;i<320*480*2;i+=38400){
HAL_SPI_Transmit_DMA(&SPI,&gImage_mn[i],38400);
while(HAL_SPI_GetState(&SPI)!=HAL_SPI_STATE_READY);
}
LCD_CS_SET;
}
/**************************************************************************/
//º¯Êý£ºvoid LCD_Set_Window(u16 sx,u16 sy,u16 width,u16 height)
//º¯Êý¹¦ÄÜ£ºÉèÖÃLCDµÄÏÔʾ´°¿Ú
//ÉèÖô°¿Ú,²¢×Ô¶¯ÉèÖûµã×ø±êµ½´°¿Ú×óÉϽÇ(sx,sy).
//sx,sy:´°¿ÚÆðÊ¼×ø±ê(×óÉϽÇ)
//width,height:´°¿Ú¿í¶ÈºÍ¸ß¶È,±ØÐë´óÓÚ0!!
//´°Ìå´óС:width*height.
//DevEBox ´óÔ½´´ÐÂ
//ÌÔ±¦µêÆÌ£ºmcudev.taobao.com
//ÌÔ±¦µêÆÌ£ºshop389957290.taobao.com
//*************************************************************************/
void LCD_Set_Window(u16 sx,u16 sy,u16 width,u16 height)
{
width=sx+width-1;
height=sy+height-1;
if(LCD_DIR_Mode==0)
{
LCD_WR_REG(lcddev.setxcmd);
LCD_WR_DATA16(sx); //ÉèÖà X·½ÏòÆðµã
LCD_WR_DATA16(width); //ÉèÖà X·½ÏòÖÕµã
LCD_WR_REG(lcddev.setycmd);
LCD_WR_DATA16(sy); //ÉèÖà Y·½ÏòÆðµã
LCD_WR_DATA16(height); //ÉèÖà Y·½ÏòÖÕµã
}
else if(LCD_DIR_Mode==1)
{
LCD_WR_REG(lcddev.setxcmd);
LCD_WR_DATA16(sx); //ÉèÖà X·½ÏòÆðµã
LCD_WR_DATA16(width); //ÉèÖà X·½ÏòÖÕµã
LCD_WR_REG(lcddev.setycmd);
LCD_WR_DATA16(sy); //ÉèÖà Y·½ÏòÆðµã
LCD_WR_DATA16(height); //ÉèÖà Y·½ÏòÖÕµã
}
else if(LCD_DIR_Mode==2)
{
LCD_WR_REG(lcddev.setxcmd);
LCD_WR_DATA16(sx); //ÉèÖà X·½ÏòÆðµã
LCD_WR_DATA16(width); //ÉèÖà X·½ÏòÖÕµã
LCD_WR_REG(lcddev.setycmd);
LCD_WR_DATA16(sy); //ÉèÖà Y·½ÏòÆðµã
LCD_WR_DATA16(height); //ÉèÖà Y·½ÏòÖÕµã
}
else if(LCD_DIR_Mode==3)
{
LCD_WR_REG(lcddev.setxcmd);
LCD_WR_DATA16(sx); //ÉèÖà X·½ÏòÆðµã
LCD_WR_DATA16(width); //ÉèÖà X·½ÏòÖÕµã
LCD_WR_REG(lcddev.setycmd);
LCD_WR_DATA16(sy); //ÉèÖà Y·½ÏòÆðµã
LCD_WR_DATA16(height); //ÉèÖà Y·½ÏòÖÕµã
}
}
void LCD_Init(void)//lcd³õʼ»¯
{
MX_SPI1_Init();
LCD_SoftRest(); //Èí¸´Î»
HAL_Delay(50); // delay 50 ms
LCD_WR_REG(0x3A);//½Ó¿ÚÏñËØ¸ñʽ
LCD_WR_DATA8(0x55);
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); //VCOM Setting
LCD_WR_DATA8(0x19);
LCD_WR_REG(0xC0); //LCM Control
LCD_WR_DATA8(0x2C);
LCD_WR_REG(0xC2); //VDV and VRH Command Enable
LCD_WR_DATA8(0x01);
LCD_WR_REG(0xC3); //VRH Set
LCD_WR_DATA8(0x12);
LCD_WR_REG(0xC4); //VDV Set
LCD_WR_DATA8(0x20);
LCD_WR_REG(0xC6); //Õý³£Ä£Ê½ÏµÄÖ¡ÂÊ¿ØÖÆ
LCD_WR_DATA8(0x0F); //֡ƵÂÊ60Ö¡
LCD_WR_REG(0xD0); //Power Control
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(0x11); //Í˳öÐÝÃß
LCD_WR_REG(0x29); //¿ªÏÔʾ
LCD_Display_Dir(LCD_DIR_Mode); //Ñ¡Ôñ--ÆÁÄ»ÏÔʾ·½Ê½
LCD_BLK_On;
LCD_RST_SET;
}
void LCD_Clear(u16 color)
{
u32 index=0;
u32 totalpoint;
LCD_Set_Window(0,0,lcddev.width,lcddev.height);//ÉèÖÃÈ«ÆÁ´°¿Ú
totalpoint=lcddev.width * lcddev.height; //µÃµ½×ܵãÊý
LCD_SetCursor(0x00,0x00); //ÉèÖùâ±êλÖÃ
LCD_WriteRAM_Prepare(); //¿ªÊ¼Ð´ÈëGRAM
for(index=0;index<totalpoint;index++)
{
LCD_WR_DATA16(color);
}
}
void LCD_Fill(u16 sx,u16 sy,u16 ex,u16 ey,u16 color)//color fill
{
u32 i;
u32 xlen=0;
LCD_Set_Window(sx,sy,ex-sx+1,ey-sy+1);//ÉèÖô°¿Ú
LCD_WR_REG(lcddev.wramcmd);
xlen=(ex-sx+1)*(ey-sy+1);//¼ÆËã³ö×ܹ²ÐèҪдÈëµÄµãÊý
LCD_WriteRAM_Prepare(); //¿ªÊ¼Ð´ÈëGRAM
for(i=0;i<=xlen*2;i+=2)
{
gram[i]=color>>8;
gram[i+1]=color;
}
LCD_TRANMITE(xlen*2);
LCD_Set_Window(0,0,lcddev.width,lcddev.height);//ÉèÖÃÈ«ÆÁ´°¿Ú
}
void LCD_Color_Fill(u16 sx,u16 sy,u16 ex,u16 ey,u16 *color)
{
u32 i;
u32 xlen=0;
LCD_Set_Window(sx,sy,ex-sx+1,ey-sy+1);
LCD_WR_REG(lcddev.wramcmd);
xlen=(ex-sx+1)*(ey-sy+1);
LCD_WriteRAM_Prepare();
for(i=0;i<=xlen;i++)
{
LCD_WR_DATA16(*color);
}
LCD_Set_Window(0,0,lcddev.width,lcddev.height);
}
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_Fast_DrawPoint(uRow,uCol,Color);//»µã --ʹÓÃÊäÈëÑÕÉ«²ÎÊý
xerr+=delta_x ;
yerr+=delta_y ;
if(xerr>distance)
{
xerr-=distance;
uRow+=incx;
}
if(yerr>distance)
{
yerr-=distance;
uCol+=incy;
}
}
}
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);
}
void LCD_Draw_Circle(u16 x0,u16 y0,u8 r, u16 Color)//»Ô²
{
int a,b;
int di;
a=0;b=r;
di=3-(r<<1); //ÅжÏϸöµãλÖõıêÖ¾
while(a<=b)
{
LCD_Fast_DrawPoint(x0+a,y0-b,Color); //5
LCD_Fast_DrawPoint(x0+b,y0-a,Color); //0
LCD_Fast_DrawPoint(x0+b,y0+a,Color); //4
LCD_Fast_DrawPoint(x0+a,y0+b,Color); //6
LCD_Fast_DrawPoint(x0-a,y0+b,Color); //1
LCD_Fast_DrawPoint(x0-b,y0+a,Color);
LCD_Fast_DrawPoint(x0-a,y0-b,Color); //2
LCD_Fast_DrawPoint(x0-b,y0-a,Color); //7
a++;
//ʹÓÃBresenhamËã·¨»Ô²
if(di<0)di +=4*a+6;
else
{
di+=10+4*(a-b);
b--;
}
}
}
void LCD_ShowChar(u16 x,u16 y,u8 num,u8 size,u16 color,u8 mode)
{
u8 temp,t1,t;
u16 y0=y;
u8 csize=(size/8+((size%8)?1:0))*(size/2); //µÃµ½×ÖÌåÒ»¸ö×Ö·û¶ÔÓ¦µãÕó¼¯ËùÕ¼µÄ×Ö½ÚÊý
//ÉèÖô°¿Ú
num=num-' ';//µÃµ½Æ«ÒƺóµÄÖµ
for(t=0;t<csize;t++)
{
if(size==12)
temp=asc2_1206[num][t]; //µ÷ÓÃ1206×ÖÌå
else if(size==16)
temp=asc2_1608[num][t]; //µ÷ÓÃ1608×ÖÌå
else if(size==24)
temp=asc2_2412[num][t]; //µ÷ÓÃ2412×ÖÌå
else return; //ûÓеÄ×Ö¿â
for(t1=0;t1<8;t1++)
{
if(temp&0x80)
LCD_Fast_DrawPoint(x,y,color);
else if(mode==0)
LCD_Fast_DrawPoint(x,y,BLACK);
temp<<=1;
y++;
if(y>=lcddev.height)return; //³¬ÇøÓòÁË
if((y-y0)==size)
{
y=y0;
x++;
if(x>=lcddev.width)return; //³¬ÇøÓòÁË
break;
}
}
}
}
u32 LCD_Pow(u8 m,u8 n)//ƽ·½
{
u32 result=1;
while(n--)result*=m;
return result;
}
void LCD_ShowNum(u16 x,u16 y,u32 num,u8 len,u8 size,u16 color)//º¯Êý¹¦ÄÜ£ºÏÔʾÊý×Ö,¸ßλΪ0,Ôò²»ÏÔʾ
{
u8 t,temp;
u8 enshow=0;
for(t=0;t<len;t++)
{
temp=(num/LCD_Pow(10,len-t-1))%10;
if(enshow==0&&t<(len-1))
{
if(temp==0)
{
LCD_ShowChar(x+(size/2)*t,y,' ',size,color,0);
continue;
}else enshow=1;
}
LCD_ShowChar(x+(size/2)*t,y,temp+'0',size,color,0);
}
}
//[7]:0,²»Ìî³ä;1,Ìî³ä0.
//[6:1]:±£Áô
//[0]:0,·Çµþ¼ÓÏÔʾ;1,µþ¼ÓÏÔʾ.
void LCD_ShowxNum(u16 x,u16 y,u32 num,u8 len,u8 size,u16 color,u8 mode)//º¯Êý¹¦ÄÜ£ºÏÔʾÊý×Ö,¸ßλΪ0,Ôò²»ÏÔʾ
{
u8 t,temp;
u8 enshow=0;
for(t=0;t<len;t++)
{
temp=(num/LCD_Pow(10,len-t-1))%10;
if(enshow==0&&t<(len-1))
{
if(temp==0)
{
if(mode&0X80)LCD_ShowChar(x+(size/2)*t,y,'0',size,color,mode&0X01);
else LCD_ShowChar(x+(size/2)*t,y,' ',size,color,mode&0X01);
continue;
}else enshow=1;
}
LCD_ShowChar(x+(size/2)*t,y,temp+'0',size,color,mode&0X01);
}
}
void LCD_ShowString(u16 x,u16 y,u16 width,u16 height,u8 size,u16 color,u8 *p,uint8_t mode)
{
u8 x0=x;
width+=x;
height+=y;
while((*p<='~')&&(*p>=' '))//ÅжÏÊDz»ÊÇ·Ç·¨×Ö·û!
{
if(x>=width){x=x0;y+=size;}
if(y>=height)break;//Í˳ö
LCD_ShowChar(x,y,*p,size,color,mode);
x+=size/2;
p++;
}
}
void DisplayButtonDown(u16 x1,u16 y1,u16 x2,u16 y2)//¹¦ÄÜÃèÊö: ÔÚÆÁÄ»ÏÔʾһ͹ÆðµÄ°´Å¥¿ò
{
LCD_DrawLine(x1,y1, x2,y1,GRAY2); //H
LCD_DrawLine(x1+1,y1+1,x2,y1+1,GRAY1); //H
LCD_DrawLine(x1, y1, x1,y2,GRAY2); //V
LCD_DrawLine(x1+1,y1+1,x1+1,y2,GRAY1); //V
LCD_DrawLine(x1, y2, x2, y2,WHITE); //H
LCD_DrawLine(x2, y1, x2, y2,WHITE); //V
}
void DisplayButtonUp(u16 x1,u16 y1,u16 x2,u16 y2)//¹¦ÄÜÃèÊö: ÔÚÆÁÄ»ÏÔʾһ°¼Ïµİ´Å¥¿ò
{
LCD_DrawLine(x1, y1, x2,y1,WHITE); //H
LCD_DrawLine(x1, y1, x1,y2,WHITE); //V
LCD_DrawLine(x1+1,y2-1,x2,y2-1,GRAY1); //H
LCD_DrawLine(x1, y2, x2,y2,GRAY2); //H
LCD_DrawLine(x2-1,y1+1,x2-1,y2,GRAY1); //V
LCD_DrawLine(x2 ,y1 ,x2,y2,GRAY2); //V
}
void Draw_Test(void)
{
LCD_Clear(WHITE); //ÇåÆÁ
LCD_DrawLine(20,64, 220,128,RED);//»®Ïߺ¯Êý
LCD_DrawLine(20,128, 220,64,RED);//»®Ïߺ¯Êý
LCD_DrawRectangle(20,64,220,128, BLUE);//»æÖÆ·½ÐÎ×´
LCD_Draw_Circle(120,96,81, BRED);//»æÖÆÔ²ÐÎ
LCD_Draw_Circle(120,96,80, BRED);//»æÖÆÔ²ÐÎ
LCD_Draw_Circle(120,96,79, BRED);//»æÖÆÔ²ÐÎ
HAL_Delay(2000);//ÑÓʱ
}
void Color_Test(void)
{
LCD_Clear(GRAY0); //ÇåÆÁ
Draw_Font16B(24,16,BLUE,"1: ÑÕÉ«Ìî³ä²âÊÔ");
LCD_Fill(5,5,lcddev.width-5,lcddev.height-5,RED);//ÉèÖÃÒ»¸ö´°¿Ú£¬Ð´ÈëÖ¸¶¨ÇøÓòÑÕÉ«
LCD_Fill(20,20,lcddev.width-20,lcddev.height-20,YELLOW);//ÉèÖÃÒ»¸ö´°¿Ú£¬Ð´ÈëÖ¸¶¨ÇøÓòÑÕÉ«
LCD_Fill(50,50,lcddev.width-50,lcddev.height-50,BLUE);//ÉèÖÃÒ»¸ö´°¿Ú£¬Ð´ÈëÖ¸¶¨ÇøÓòÑÕÉ«
LCD_Fill(80,100,lcddev.width-80,lcddev.height-80,MAGENTA);//ÉèÖÃÒ»¸ö´°¿Ú£¬Ð´ÈëÖ¸¶¨ÇøÓòÑÕÉ«
HAL_Delay(2000);
LCD_Clear(WHITE);
Draw_Test();//»æÍ¼º¯Êý²âÊÔ
HAL_Delay(300);//ÑÓʱ
LCD_Clear(BLACK);
HAL_Delay(300);//ÑÓʱ
LCD_Clear(RED);
HAL_Delay(300);//ÑÓʱ
LCD_Clear(YELLOW);
HAL_Delay(300);//ÑÓʱ
LCD_Clear(GREEN);
HAL_Delay(300);//ÑÓʱ
LCD_Clear(BLUE);
HAL_Delay(300);//ÑÓʱ
}
uint16_t D_Color=BLUE; //µãÕóÑÕÉ«
uint16_t B_Color=WHITE; //±³¾°ÑÕÉ«
void Font_Test(void)
{
LCD_Clear(GRAY0);
Draw_Font16B(24,16,BLUE,"2: ÎÄ×ÖÏÔʾ²âÊÔ");
HAL_Delay(1000);
LCD_Clear(GRAY0);
Draw_Font24B(16,4,BLACK,"DevEBox-´óÔ½´´ÐÂ");
Draw_Font24B(48,32,BLACK,"Òº¾§ÆÁ²âÊÔ");
Draw_Font16B(24,80, BLACK,"ǶÈëʽ¿ª·¢Íø");
Draw_Font16B(24,96, GREEN,"ÖÐÎIJâÊÔ");
Draw_Font16B(24,112,BLUE,"רעҺ¾§Åú·¢");
Draw_Font16B(24,128,RED, "È«³Ì¼¼ÊõÖ§³Ö");
Draw_Font16B(16,144,BLUE,"F: mcudev.taobao.com");
Draw_Font16B(16,160,BLUE,"F: shop389957290.taobao.com");
Draw_Font16B(16,176,RED,"0123456789 ABCDEFGHIJKLMNOPQRSTUVWXYZ abcdefghijklmnopqrstuvwxyz");
HAL_Delay(3000);
LCD_Clear(GRAY0);
}
void Demo_Menu(void)
{
LCD_Clear(GRAY0); //ÇåÆÁ
Draw_Font24B(16,4,MAGENTA,"DevEBox-´óÔ½´´ÐÂ");
Draw_Font24B(48,32,MAGENTA,"Òº¾§ÆÁ²âÊÔ");
DisplayButtonUp(16,64,224,88); //x1,y1,x2,y2
Draw_Font16B(48,68,BLUE,"1: ÑÕÉ«Ìî³ä²âÊÔ");
DisplayButtonUp(16,104,224,128); //x1,y1,x2,y2
Draw_Font16B(48,108,BLUE,"2: ÎÄ×ÖÏÔʾ²âÊÔ");
DisplayButtonUp(16,144,224,168); //x1,y1,x2,y2
Draw_Font16B(48,148,BLUE,"3: ͼƬÏÔʾ²âÊÔ");
Draw_Font16B(16,180,RED,"F: mcudev.taobao.com");
Draw_Font16B(16,196,RED,"F: shop389957290.taobao.com");
HAL_Delay(2000);//ÑÓʱ
Color_Test();
Font_Test();
}
lcd这部分直接移植就好了,不用都一样
需要注意
HAL_SPI_Transmit_DMA(&SPI,&gram[i],38400);
while(HAL_SPI_GetState(&SPI)!=HAL_SPI_STATE_READY);
由于DMA传输不需要CPU参与,是不阻塞cpu的,在我写的DMA刷屏函数中使用循环发送,如果不主动阻塞的话就会发送前一个没发完后一个又来了,产生BUSY,所以主动读标志位,阻塞到发送完成.
由于使用的HAL库,发送大小有int范围限制,所以选取一个大小差不多的范围,38400传输8次刚刚好
另外我只写了刷新全屏的,局部刷新也是一个原理需要使用开窗和指定位置操作,随后将对应大小数组刷过去.
MAIN.C
不知道为什么触摸和dma有点冲突,会导致dma卡死
/* USER CODE BEGIN Header */
/**
******************************************************************************
* @file : main.c
* @brief : Main program body
******************************************************************************
* @attention
*
* Copyright (c) 2024 STMicroelectronics.
* All rights reserved.
*
* This software is licensed under terms that can be found in the LICENSE file
* in the root directory of this software component.
* If no LICENSE file comes with this software, it is provided AS-IS.
*
******************************************************************************
*/
/* USER CODE END Header */
/* Includes ------------------------------------------------------------------*/
#include "main.h"
#include "adc.h"
#include "dma.h"
#include "i2c.h"
#include "spi.h"
#include "tim.h"
#include "usart.h"
#include "gpio.h"
/* Private includes ----------------------------------------------------------*/
/* USER CODE BEGIN Includes */
#include "lcd.h"
#include "GT911.h"
//#include "Dis_Picture.h"
#include "stdio.h"
/* USER CODE END Includes */
/* Private typedef -----------------------------------------------------------*/
/* USER CODE BEGIN PTD */
/* USER CODE END PTD */
/* Private define ------------------------------------------------------------*/
/* USER CODE BEGIN PD */
/* USER CODE END PD */
/* Private macro -------------------------------------------------------------*/
/* USER CODE BEGIN PM */
int num=0;
/* USER CODE END PM */
/* Private variables ---------------------------------------------------------*/
/* USER CODE BEGIN PV */
/* USER CODE END PV */
/* Private function prototypes -----------------------------------------------*/
void SystemClock_Config(void);
static void MPU_Config(void);
/* USER CODE BEGIN PFP */
/* USER CODE END PFP */
/* Private user code ---------------------------------------------------------*/
/* USER CODE BEGIN 0 */
/* USER CODE END 0 */
/**
* @brief The application entry point.
* @retval int
*/
int main(void)
{
/* USER CODE BEGIN 1 */
int i=0;
/* USER CODE END 1 */
/* MPU Configuration--------------------------------------------------------*/
MPU_Config();
/* MCU Configuration--------------------------------------------------------*/
/* Reset of all peripherals, Initializes the Flash interface and the Systick. */
HAL_Init();
/* USER CODE BEGIN Init */
/* USER CODE END Init */
/* Configure the system clock */
SystemClock_Config();
/* USER CODE BEGIN SysInit */
/* USER CODE END SysInit */
/* Initialize all configured peripherals */
MX_GPIO_Init();
MX_DMA_Init();
MX_USART1_UART_Init();
MX_ADC3_Init();
MX_I2C2_Init();
MX_TIM2_Init();
MX_SPI1_Init();
MX_TIM8_Init();
/* USER CODE BEGIN 2 */
GT911_INIT();
LCD_Init();
LCD_QCLEAR(GREEN);
Delay(100);
LCD_QCLEAR_DMA(RED);
//LCD_QCLEAR(GREEN);
/* USER CODE END 2 */
/* Infinite loop */
/* USER CODE BEGIN WHILE */
while (1)
{
/* USER CODE END WHILE */
/* USER CODE BEGIN 3 */
SHOW_PIC_DMA();
LCD_QCLEAR(WHITE);
}
/* USER CODE END 3 */
}
/**
* @brief System Clock Configuration
* @retval None
*/
void SystemClock_Config(void)
{
RCC_OscInitTypeDef RCC_OscInitStruct = {0};
RCC_ClkInitTypeDef RCC_ClkInitStruct = {0};
/** Supply configuration update enable
*/
HAL_PWREx_ConfigSupply(PWR_LDO_SUPPLY);
/** Configure the main internal regulator output voltage
*/
__HAL_PWR_VOLTAGESCALING_CONFIG(PWR_REGULATOR_VOLTAGE_SCALE1);
while(!__HAL_PWR_GET_FLAG(PWR_FLAG_VOSRDY)) {}
/** Initializes the RCC Oscillators according to the specified parameters
* in the RCC_OscInitTypeDef structure.
*/
RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSI;
RCC_OscInitStruct.HSIState = RCC_HSI_DIV1;
RCC_OscInitStruct.HSICalibrationValue = RCC_HSICALIBRATION_DEFAULT;
RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON;
RCC_OscInitStruct.PLL.PLLSource = RCC_PLLSOURCE_HSI;
RCC_OscInitStruct.PLL.PLLM = 4;
RCC_OscInitStruct.PLL.PLLN = 50;
RCC_OscInitStruct.PLL.PLLP = 2;
RCC_OscInitStruct.PLL.PLLQ = 4;
RCC_OscInitStruct.PLL.PLLR = 8;
RCC_OscInitStruct.PLL.PLLRGE = RCC_PLL1VCIRANGE_3;
RCC_OscInitStruct.PLL.PLLVCOSEL = RCC_PLL1VCOWIDE;
RCC_OscInitStruct.PLL.PLLFRACN = 0;
if (HAL_RCC_OscConfig(&RCC_OscInitStruct) != HAL_OK)
{
Error_Handler();
}
/** Initializes the CPU, AHB and APB buses clocks
*/
RCC_ClkInitStruct.ClockType = RCC_CLOCKTYPE_HCLK|RCC_CLOCKTYPE_SYSCLK
|RCC_CLOCKTYPE_PCLK1|RCC_CLOCKTYPE_PCLK2
|RCC_CLOCKTYPE_D3PCLK1|RCC_CLOCKTYPE_D1PCLK1;
RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_PLLCLK;
RCC_ClkInitStruct.SYSCLKDivider = RCC_SYSCLK_DIV1;
RCC_ClkInitStruct.AHBCLKDivider = RCC_HCLK_DIV2;
RCC_ClkInitStruct.APB3CLKDivider = RCC_APB3_DIV2;
RCC_ClkInitStruct.APB1CLKDivider = RCC_APB1_DIV2;
RCC_ClkInitStruct.APB2CLKDivider = RCC_APB2_DIV2;
RCC_ClkInitStruct.APB4CLKDivider = RCC_APB4_DIV2;
if (HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_2) != HAL_OK)
{
Error_Handler();
}
}
/* USER CODE BEGIN 4 */
/* USER CODE END 4 */
/* MPU Configuration */
void MPU_Config(void)
{
MPU_Region_InitTypeDef MPU_InitStruct = {0};
/* Disables the MPU */
HAL_MPU_Disable();
/** Initializes and configures the Region and the memory to be protected
*/
MPU_InitStruct.Enable = MPU_REGION_ENABLE;
MPU_InitStruct.Number = MPU_REGION_NUMBER0;
MPU_InitStruct.BaseAddress = 0x0;
MPU_InitStruct.Size = MPU_REGION_SIZE_4GB;
MPU_InitStruct.SubRegionDisable = 0x87;
MPU_InitStruct.TypeExtField = MPU_TEX_LEVEL0;
MPU_InitStruct.AccessPermission = MPU_REGION_NO_ACCESS;
MPU_InitStruct.DisableExec = MPU_INSTRUCTION_ACCESS_DISABLE;
MPU_InitStruct.IsShareable = MPU_ACCESS_SHAREABLE;
MPU_InitStruct.IsCacheable = MPU_ACCESS_NOT_CACHEABLE;
MPU_InitStruct.IsBufferable = MPU_ACCESS_NOT_BUFFERABLE;
HAL_MPU_ConfigRegion(&MPU_InitStruct);
/* Enables the MPU */
HAL_MPU_Enable(MPU_PRIVILEGED_DEFAULT);
}
/**
* @brief This function is executed in case of error occurrence.
* @retval None
*/
void Error_Handler(void)
{
/* USER CODE BEGIN Error_Handler_Debug */
/* User can add his own implementation to report the HAL error return state */
__disable_irq();
while (1)
{
}
/* USER CODE END Error_Handler_Debug */
}
#ifdef USE_FULL_ASSERT
/**
* @brief Reports the name of the source file and the source line number
* where the assert_param error has occurred.
* @param file: pointer to the source file name
* @param line: assert_param error line source number
* @retval None
*/
void assert_failed(uint8_t *file, uint32_t line)
{
/* USER CODE BEGIN 6 */
/* User can add his own implementation to report the file name and line number,
ex: printf("Wrong parameters value: file %s on line %d\r\n", file, line) */
/* USER CODE END 6 */
}
#endif /* USE_FULL_ASSERT */
代码打包
链接:https://pan.baidu.com/s/1XfTWm7aT6FEZASfxmKD34w
提取码:elc8
6739





