SSD1963驱动板原理图
- 格式:pdf
- 大小:423.36 KB
- 文档页数:2
固态硬盘工作原理固态硬盘(Solid State Drives)简称 SSD,是用固态电子存储芯片阵列而制成的硬盘,由控制单元和存储单元组成。
分类固态硬盘的存储介质分为两种:一种是闪存(FLASH 芯片),另外一种是DRAM。
基于闪存的固态硬盘是固态硬盘的主要类别,主要由控制芯片,缓存芯片和闪存芯片构成。
其中控制芯片主要承担数据调配、数据中转以及连接闪存芯片和外部 SATA 接口。
缓存芯片主要用于辅助控制芯片进行数据处理。
而闪存芯片则是用于数据读写。
此外,基于闪存的固态硬盘中存储单元又分:SLC(Single Level Cell)单层存储单元、MLC(Multi Leveled Cell)多层存储单元以及 TLC( Triple-cell- per-bit)三层存储单元等。
在 SLC 架构中,每 Cell 可存储 1bit 数据, MLC 架构中每 Cell 可以存储2bit 数据,而 TLC 架构每 Cell 可以存储 3 bit 数据。
存储原理Flash 的最小存储单元是晶浮栅晶体管,对应于磁盘中的一个 bit 的存储单元。
SSD 中,在存储单元晶体管的栅(Gate)中,注入不同数量的电子,通过改变栅的导电性能,来改变晶体管的导通效果,从而实现对不同状态的记录和识别。
在 SLC 架构中,栅中的电子数目多与少,带来的只有两种导通状态,对应读出的数据就只有 0/1;MLC 架构中,栅中电子数目不同时,可以读出多种状态,能够对应出 00/01/10/11 等不同数据。
因此,SSD 数据处理都要进行加电处理,加电的过程等同于 HDD 硬盘的数据写入操作,断电的过程电位恢复,相当于 HDD 硬盘的擦除。
数据完整的一次 P/E 循环就是 NAND 的写入循环。
因为 P/E 循环次数是有限的,这也就直接影响到 SSD 的寿命。
但是根据存储架构的不同,SDD 的寿命也是有差别的。
由于 SLC 结构简单,在写入数据时电压变化的区间小,所以寿命较长,传统的 SLC NAND 闪存可以经受 10 万次的读写。
驱动桥原理图驱动桥是一种用于控制电机或其他电动设备的电路,它可以实现电机的正转、反转以及制动等功能。
在电动车、工业机械等领域广泛应用,是现代电气控制领域的重要组成部分。
本文将介绍驱动桥的原理图及其工作原理。
驱动桥原理图主要由功率电路和控制电路两部分组成。
功率电路包括电源模块、MOS管和电机,控制电路包括驱动芯片、电流传感器、电压传感器等。
下面我们将对这两部分进行详细介绍。
首先是功率电路部分。
电源模块为整个电路提供电源,MOS管是功率开关管,可以控制电机的正转和反转。
电机是驱动桥的输出部分,根据MOS管的导通与截止状态,实现电机的正转、反转和制动。
功率电路的设计需要考虑电机的功率、电压、电流等参数,以确保电路能够正常工作。
其次是控制电路部分。
驱动芯片是控制电路的核心部分,它接收外部控制信号,并通过内部逻辑电路控制MOS管的导通与截止。
电流传感器和电压传感器用于监测电机的电流和电压,以实现对电机的闭环控制。
控制电路的设计需要考虑信号的精确度、抗干扰能力以及系统的稳定性。
驱动桥的工作原理是通过控制MOS管的导通与截止状态,实现对电机的控制。
在正转状态下,控制芯片输出相应的信号,使得MOS管导通,电机正转;在反转状态下,控制芯片输出相应的信号,使得MOS管导通,电机反转;在制动状态下,通过控制MOS管的导通与截止,实现对电机的制动。
同时,通过电流传感器和电压传感器监测电机的电流和电压,实现对电机的闭环控制,提高系统的稳定性和精度。
总之,驱动桥是一种重要的电机控制电路,它通过功率电路和控制电路实现对电机的控制。
在实际应用中,需要根据具体的要求设计合适的驱动桥原理图,并考虑功率、电压、电流、稳定性等因素,以确保电路能够正常、稳定地工作。
希望本文对驱动桥的原理图及工作原理有所帮助,谢谢阅读!。
SSD基本工作原理SSD(Solid State Disk),即固态存储,它用固态电子存储芯片阵列而制成的硬盘,由控制单元和存储单元组成,其一般可以分为两种方式:基于闪存的SSD (采用FLASH芯片作为存储介质)和基于DRAM的SSD(采用DRAM作为存储介质)。
传统硬盘的机械特性严重限制了数据读取、写入的速度及性能;SSD采用FLASH存储介质,它内部没有机械结构,因此没有数据查找时间、延迟时间和寻道时间。
对SSD而言,其读取数据的过程就是一个解析地址的过程,因此,其数据读取的速度非常快。
SSD的写操作比较特殊,其最小写入单元为4KB,称为页(page),当写入空白位置时可以按照4KB的单位写入,但是如果需要改写某个单元时,则需要一个额外的擦除动作,擦除的单位(块block)一般是128个page,如果向一个空白的page写入信息时,可以直接写入而无需擦除,但是如果需要改写某个存储单元的数据,必须首先将整个block读入缓存,然后修改数据,并擦除整个block的数据,最后将整个block写入,很显然,SSD改写数据的代价很高,SSD的这个特性,称之为erase-before-write。
HOST是通过逻辑地址块(LBA)访问SSD的,每个LBA代表着一个Sector (一般为512B大小),操作系统一般以4K为单位访问SSD,把HOST访问SSD 的基本单元称作用户页(Host Page)。
而在SSD内部,SSD主控与FLASH之间是以FLASH Page为基本单元访问FLASH的,称FLASH Page为物理页(Physical Page)。
HOST每写入一个Host Page,SSD主控会找Physical Page把Host数据写入,SSD内部同时记录了这样一条映射(Map)。
有了这样一个映射关系后,下次HOST需要读某个Host Page 时,SSD就知道从FLASH的哪个位置把数据读取上来。
基于SSD1963控制器的液晶显示模块设计赵彩虹;刘凯;尹涓【摘要】为了满足嵌入式工业控制系统终端显示的需要,提出了一种基于微处理器R1610和LCD控制器SSD1963的液晶显示模块的设计方法;详细阐述了硬件接口电路的设计和控制软件的编程,重点介绍了R1610、SSD1963以及TFT液晶屏AT070TN83之间的硬件连接方法,分析了SSD1963液晶控制的使用方法以及针对液晶屏显示时序的系统设置;进行了显示控制测试,通过该显示模块实现了图像在液晶屏上的显示;测试结果表明,硬件设计和控制软件设计能够满足显示要求,显示效果良好;文章提出的显示模块设计方法同样适用于其他液晶屏的显示控制,具有一定的应用前景和参考价值.【期刊名称】《计算机测量与控制》【年(卷),期】2015(023)011【总页数】3页(P3797-3799)【关键词】SSD1963;液晶显示模块;R1610;AT070TN83【作者】赵彩虹;刘凯;尹涓【作者单位】南京航空航天大学金城学院机电工程系,南京211156;南京航空航天大学机电学院,南京210016;南京航空航天大学金城学院机电工程系,南京211156【正文语种】中文【中图分类】TN141.9液晶显示模块应用于人机交互过程中的文本及图形信息的显示[1]。
嵌入式工业控制系统中要求实时显示运行状态、系统参数以及相关图表图形等信息,采用液晶屏显示模块作为终端显示设备,显示内容丰富,直观性强[2]。
本文基于金丽科技公司(RDC)的X86系列的微处理器R1610和晶门科技公司(SolomonSystech)的SSD1963液晶显示控制器,采用群创公司(Innolux)的AT070TN83液晶屏,进行相关硬件电路和控制软件的设计,实现液晶屏的图形显示功能。
液晶显示模块结构框图如图1所示。
系统控制器采用微处理器控制,把系统信息以文本、图表的形式发送至LCD控制器;LCD控制器根据接收到的显示指令,通过LCD驱动器,以一定的扫描时序将需要显示的内容传输给液晶屏实时地进行显示。
首页阅览室馆友我的图书馆来自:mcu_mouse > 嵌入式C语言配色:字号SSD1963的样例程序2010-12-01 | 阅:1803 转:28 | 分享//===============================typedef union {unsigned char UByte[2];unsigned int UInt;} UWORD;void SSD1963Data_16(uchar sdataH,uchar sdataL);void SSD1963Data1_16(uint dat);void SSD1963Command_16(uint cmd);void SetPixel(uint Col,uint Page,uint color); //显示一个相素点uint GetPixel(uint Col,uint Page);//得到一个像素点/******************************************************SSD1963的Conf脚,用来控制读写的方式,如果为0 则为6800总线MODE如果位1 ,则为8080总线。
下面的定义是8080 MODE(默认情况下为8080),可以通过修改Conf 跳点来修改读写式。
******************************************************/void SSD1963Command_8(uchar cmd);void SSD1963Data_8(uchar sdata);uchar GetSSD1963Data_8();uint GetSSD1963Data_16();void ReadSSD1963Set();#define SetSSD1963RD() SetBit(P4,4) #define SetSSD1963WR() SetBit(P4,5)#define SetSSD1963CS() SetBit(P4,2)#define SetSSD1963DC() SetBit(P4,3) #define SetSSD1963Reset() SetBit(P4,1) #define SetSSD1963Wait() SetBit(p4,0) #define ClrSSD1963RD() ClrBit(P4,4)#define ClrSSD1963CS() ClrBit(P4,2)#define ClrSSD1963DC() ClrBit(P4,3)#define ClrSSD1963Reset() ClrBit(P4,1)#define ClrSSD1963Wait() ClrBit(p4,0)#define DataPortL P1#define DataPortH P2//UWORD 是一个结构体//注意在给1963写命令时,只能用数据线的低8位来传输数据。
SSD固态硬盘的结构和基本工作原理概述我们都知道,早期的电脑CPU是可以直接从硬盘上面读取数据进行处理的,随着科技的进步,时代的发展,计算机硬件的发展速度也是极其迅猛。
CPU主频的不断提升,从单核到双核,再到多核;CPU 的处理速度越来越快,而硬盘的的读写速度已经远远跟不上CPU的读写速度,后来增加了内存这个读写速度相对较快的缓存,而内存也是蓬勃到发展,从SDRAM到DDR,从DDR到DDR2再到DDR3,但是无论怎样,内存缓存速度还是跟不上CPU的运算处理速度,后来便在CPU中增加了快速缓存机制!而硬盘这个持久化存储器呢?之前的文章,聊到了机械硬盘的结构和工作原理,今天就来聊一聊SSD固态硬盘的结构和基本工作原理,如理解有所变差,或文章有所不足,皆因水平所限!硬盘的发展在不断的科技进步中快速提升,从容量以及速度再到接口方面。
从早期的PATA变成SATA,SCSI变到SAS,以及垂直记录技术在容量上的突破,但这些进步亦未能改变磁盘的记录方式。
随着人们对数据需求增多,存储系统的瓶颈越来越明显。
而在嵌入式领域移动设备和工业自动化控制等恶劣环境下,传统硬盘机械结构已经无法满足要求,而所有这一切随着固态存储(SSD)的到来而发生了改变。
传统的机械硬盘(HDD)运行主要是靠机械驱动头,包括马达、盘片、磁头摇臂等必需的机械部件,它必须在快速旋转的磁盘上移动至访问位置,至少95%的时间都消耗在机械部件的动作上。
SSD却不同机械构造,无需移动的部件,主要由主控与闪存芯片组成的SSD可以以更快速度和准确性访问驱动器到任何位置。
传统机械硬盘必须得依靠主轴主机、磁头和磁头臂来找到位置,而SSD用集成的电路代替了物理旋转磁盘,访问数据的时间及延迟远远超过了机械硬盘。
SSD有如此的“神速”,完全得益于内部的组成部件:主控--闪存--固件算法。
主控、闪存及固件算法三者的关系:SSD最重要的三个组件就是NAND闪存,控制器及固件。
NAND工作原理由于本人之前的C300测试贴中的部分原理解释不是最“傻瓜”式,造成很多朋友的困惑,在群里在论坛里讨论时,发现很多朋友的理解都还是有问题,故此特地开一个帖子解释的更“傻瓜”点。
首先我们来看下,作为L63B颗粒,Intel/Micron的34nm 4KB page的颗粒,内部结构是这样的。
1个page为4KB,1个Block为256个page组成,1个Plane由2048个Block组成,2个Plane组成1个Die,也就是最小的芯片(4GB),X25-M 80G Gen2 SSD上面我们看到10个颗粒,每个颗粒是8GB的,就是由2个Die封装起来的。
Page为最小的读写单位,Block为最小的擦除/编程单位。
(我知道这些很多人都知道,重复重复再重复我也很烦)。
接下来,我来假设一个主控和颗粒环境:1个8通道8位的主控连接到8个Die上,为了解释方便,我这里就画了每个Die里的第一个Block。
(实际当然要复杂很多)好了,接下来我们要进行读写了,看清楚,这下面的东西才是你们最想知道的。
1. 现在我先对主机发送一条命令,要求写入4KB。
主控接到主机发来的指令后,往颗粒1的Block1里写入了1个4KB(占1Page)。
2.继续写入8KB。
主控接到主机发来的指令后,往颗粒2的Block1里和颗粒3的Block1里各写入4KB。
好了,我们来举一反三,如果写入的是32KB,那么主控就会一下子往每个颗粒的Block1里写入4KB,这样就能发挥出这个SSD主控理论最大的写入带宽,相对4KB来说最好情况下我们可以得到8倍的速度(取决于主控对通道的优化,颗粒当前的文件状况等等)。
这样你们就会知道为啥4KB的写入慢,而持续写入SSD并不慢的道理了吧,实际情况下当然不会都写Block1,我这里只是想解释的简单点。
这个类似RAID 0的操作模式就是大部分的SSD内部操作情况。
上面是写入的情况,对于读取自然也是如此,4KB的读取就从一个Block里读,而32KB的话就从8个Block里拿,速度是不是8倍提升取决于要读取的数据是不是平均分布在每个颗粒的Block里,如果32KB数据是存储在图中颗粒1~4的Block1里的(每个Block假设8KB),那么读取就最多只有4倍的提升了,这也是为啥文件越小传输率越低的道理。
SSD1963初始化/**************************************************************** mili开发板** LCD驱动代码** 版本:V1.0** 论坛:/doc/9fa31eb11a37f111f1855bd2.html** 淘宝:/doc/9fa31eb11a37f111f1855bd2.html /** 技术⽀持群:105339839***************************************************************//* Includes ------------------------------------------------------------------*/#include "stm32f10x.h"#include "hardware.h"#include "ili932x.h"#include "font.h"#includeunsigned int HDP=479;unsigned int HT=531;unsigned int HPS=43;unsigned int LPS=8;unsigned char HPW=10;unsigned int VDP=271;unsigned int VT=288;unsigned int VPS=12;unsigned int FPS=4;unsigned char VPW=10;u32 POINT_COLOR = BLUE,BACK_COLOR = WHITE; /* 分别设置点的颜⾊和底⾊ *//******************************************** 函数名:LCD_GPIO_Config* 描述:根据FSMC配置LCD的I/O*********************************************/void LCD_GPIO_Config(void){GPIO_InitTypeDef GPIO_InitStructure;/* 使能FSMC时钟*/RCC_AHBPeriphClockCmd(RCC_AHBPeriph_FSMC, ENABLE);/* 使能FSMC对应相应管脚时钟 D E */RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOC|RCC_APB2Periph_GPIOD|RCC_APB2Periph_GPIOE,ENABLE); GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;/* 配置LCD背光控制管脚*/GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8;GPIO_Init(GPIOC, &GPIO_InitStructure);/* 配置FSMC相对应的数据线,FSMC-D0~D15: PD 14 15 0 1,PE 7 8 9 10 11 12 13 14 15,PD 8 9 10*/GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0 | GPIO_Pin_1 | GPIO_Pin_8 | GPIO_Pin_9 |GPIO_Pin_10 | GPIO_Pin_14 | GPIO_Pin_15;GPIO_Init(GPIOD, &GPIO_InitStructure);GPIO_InitStructure.GPIO_Pin = GPIO_Pin_7 | GPIO_Pin_8 | GPIO_Pin_9 | GPIO_Pin_10 |GPIO_Pin_11 | GPIO_Pin_12 | GPIO_Pin_13 | GPIO_Pin_14 |GPIO_Pin_15;GPIO_Init(GPIOE, &GPIO_InitStructure);/* 配置FSMC相对应的控制线* PD4-FSMC_NOE :LCD-RD* PD5-FSMC_NWE :LCD-WR* PD7-FSMC_NE1 :LCD-CS* PD11-FSMC_A16 :LCD-DC*/GPIO_InitStructure.GPIO_Pin = GPIO_Pin_4;GPIO_Init(GPIOD, &GPIO_InitStructure);GPIO_InitStructure.GPIO_Pin = GPIO_Pin_5;GPIO_Init(GPIOD, &GPIO_InitStructure);GPIO_InitStructure.GPIO_Pin = GPIO_Pin_7;GPIO_Init(GPIOD, &GPIO_InitStructure);GPIO_InitStructure.GPIO_Pin = GPIO_Pin_11 ;GPIO_Init(GPIOD, &GPIO_InitStructure);/* TFT control gpio init *///GPIO_SetBits(GPIOC, GPIO_Pin_10); // 背光打开GPIO_SetBits(GPIOD, GPIO_Pin_4); // RD = 1GPIO_SetBits(GPIOD, GPIO_Pin_5); // WR = 1GPIO_SetBits(GPIOD, GPIO_Pin_7); // CS = 1}/******************************************** 函数名:LCD_FSMC_Config* 描述:LCD FSMC 模式配置*********************************************/void LCD_FSMC_Config(void){FSMC_NORSRAMInitTypeDef FSMC_NORSRAMInitStructure;FSMC_NORSRAMTimingInitTypeDef p;p.FSMC_AddressSetupTime = 0x02; //地址建⽴时间p.FSMC_AddressHoldTime = 0x00; //地址保持时间p.FSMC_DataSetupTime = 0x05; //数据建⽴时间p.FSMC_BusTurnAroundDuration = 0x00;p.FSMC_CLKDivision = 0x00;p.FSMC_DataLatency = 0x00;p.FSMC_AccessMode = FSMC_AccessMode_B;// ⼀般使⽤模式B来控制LCDFSMC_NORSRAMInitStructure.FSMC_Bank = FSMC_Bank1_NORSRAM1;FSMC_NORSRAMInitStructure.FSMC_DataAddressMux = FSMC_DataAddressMux_Disable; FSMC_NORSRAMInitStructure.FSMC_MemoryType = FSMC_MemoryType_NOR;FSMC_NORSRAMInitStructure.FSMC_MemoryDataWidth = FSMC_MemoryDataWidth_16b;FSMC_NORSRAMInitStructure.FSMC_BurstAccessMode = FSMC_BurstAccessMode_Disable; FSMC_NORSRAMInitStructure.FSMC_WaitSignalPolarity = FSMC_WaitSignalPolarity_Low;FSMC_NORSRAMInitStructure.FSMC_WrapMode = FSMC_WrapMode_Disable;FSMC_NORSRAMInitStructure.FSMC_WaitSignalActive = FSMC_WaitSignalActive_BeforeWaitState; FSMC_NORSRAMInitStructure.FSMC_WriteOperation = FSMC_WriteOperation_Enable;FSMC_NORSRAMInitStructure.FSMC_WaitSignal = FSMC_WaitSignal_Disable;FSMC_NORSRAMInitStructure.FSMC_ExtendedMode = FSMC_ExtendedMode_Disable;FSMC_NORSRAMInitStructure.FSMC_WriteBurst = FSMC_WriteBurst_Disable;FSMC_NORSRAMInitStructure.FSMC_ReadWriteTimingStruct = &p;FSMC_NORSRAMInitStructure.FSMC_WriteTimingStruct = &p;FSMC_NORSRAMInit(&FSMC_NORSRAMInitStructure);/* 使能 FSMC Bank1_SRAM Bank */FSMC_NORSRAMCmd(FSMC_Bank1_NORSRAM1, ENABLE);}/******************************************************************************* 函数名称: LCD_Write_Reg** 功能描述: 写指令及数据** 作者: Dream** ⽇期: 2010年12⽉06⽇*****************************************************************************/void LCD_WriteReg(uint16_t LCD_Reg,uint16_t LCD_Dat){Write_Cmd(LCD_Reg);Write_Dat(LCD_Dat);}/******************************************************************************* 函数名称: Write_Cmd** 功能描述: 写指令** 作者: Dream** ⽇期: 2010年12⽉06⽇*****************************************************************************/void Write_Cmd(uint16_t LCD_Reg){// LCD_CS = 0;// LCD_RS = 0;// GPIOC->ODR = (GPIOC->ODR&0xff00)|(LCD_Reg&0x00ff);// GPIOB->ODR = (GPIOB->ODR&0x00ff)|(LCD_Reg&0xff00);// LCD_WR = 0;// LCD_WR = 1;// LCD_CS = 1;((*(__IO u16 *) (Bank1_LCD_C)) = ((u16) LCD_Reg));}/******************************************************************************* 函数名称: Write_Dat**功能描述: 写数据** 作者: Dream** ⽇期: 2010年12⽉06⽇*****************************************************************************/void Write_Dat(uint16_t LCD_Dat){// LCD_CS = 0;// LCD_RS = 1;// GPIOC->ODR = (GPIOC->ODR&0xff00)|(LCD_Dat&0x00ff);// GPIOB->ODR = (GPIOB->ODR&0x00ff)|(LCD_Dat&0xff00);// LCD_WR = 0;// LCD_WR = 1;// LCD_CS = 1;((*(__IO u16 *) (Bank1_LCD_D)) = ((u16)(LCD_Dat)));}/******************************************************************************* 函数名称: LCD_ReadReg** 功能描述: 读指令** 作者: Dream** ⽇期: 2010年12⽉06⽇*****************************************************************************/uint16_t LCD_ReadReg(uint16_t LCD_Reg){// uint16_t temp;// Write_Cmd(LCD_Reg); //写⼊要读的寄存器号//// GPIOB->CRH = (GPIOB->CRH & 0x00000000) | 0x44444444; //将端⼝⾼8位配置成输⼊// GPIOC->CRL = (GPIOC->CRL & 0x00000000) | 0x44444444; //将端⼝低8位配置成输⼊// LCD_CS = 0;// LCD_RS = 1;// LCD_RD = 0;// temp = ((GPIOB->IDR&0xff00)|(GPIOC->IDR&0x00ff)); //读取数据(读寄存器时,并不需要读2次) // LCD_RD = 1;// LCD_CS = 1;// GPIOB->CRH = (GPIOB->CRH & 0x00000000) | 0x33333333; //释放端⼝⾼8位为输出// GPIOC->CRL = (GPIOC->CRL & 0x00000000) | 0x33333333; //释放端⼝低8位为输出// return temp;/* Write 16-bit Index (then Read Reg) */LCD->LCD_REG = LCD_Reg;/* Read 16-bit Reg */return (LCD->LCD_RAM);}/******************************************************************************* 函数名称: LCD_ReadDat** 功能描述: 读数据** 作者: Dream** ⽇期: 2010年12⽉06⽇*****************************************************************************/uint16_t LCD_ReadDat(){// uint16_t temp;//// GPIOE->CRH = (GPIOE->CRH & 0x00000000) | 0x44444444; //将端⼝⾼8位配置成输⼊// GPIOE->CRL = (GPIOE->CRL & 0x00000000) | 0x44444444; //将端⼝低8位配置成输⼊// LCD_CS = 0;// LCD_RS = 1;// LCD_RD = 0;// temp = ((GPIOB->IDR&0xff00)|(GPIOC->IDR&0x00ff)); //读取数据(读寄存器时,并不需要读2次) // LCD_RD = 1;// LCD_CS = 1;// GPIOE->CRH = (GPIOE->CRH & 0x00000000) | 0x33333333; //释放端⼝⾼8位为输出// GPIOE->CRL = (GPIOE->CRL & 0x00000000) | 0x33333333; //释放端⼝低8位为输出//// return temp;u16 tmp_color = 0;u8 Green = 0,Red=0,Black=0;Green = *((__IO u8 *)(Bank1_LCD_D)); /*第⼀个数据⽆效*/Green = *((__IO u8 *)(Bank1_LCD_D));Red = *((__IO u8 *)(Bank1_LCD_D));Black = *((__IO u8 *)(Bank1_LCD_D));tmp_color = (u16)((((u16)Red>>3)<<11)|(((u16)Green>>2)<<5)|((u16)Black>>3));return(tmp_color);}/******************************************************************************* 函数名称: LCD_Configuration** 功能描述: LCD_IO⼝配置** 作者: Dream** ⽇期: 2010年12⽉06⽇*****************************************************************************/void LCD_Configuration(){GPIO_InitTypeDef GPIO_InitStructure;RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB | RCC_APB2Periph_GPIOC,ENABLE); /* 配置数据IO 连接到GPIOB *********************/GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8 | GPIO_Pin_9 | GPIO_Pin_10 | GPIO_Pin_11| GPIO_Pin_12 | GPIO_Pin_13 | GPIO_Pin_14 | GPIO_Pin_15;GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP; // 推挽输出⽅式GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; // 输出IO⼝最⼤最速为50MHZ GPIO_Init(GPIOB, &GPIO_InitStructure);/* 配置控制IO 连接到PD12.PD13.PD14.PD15 *********************/GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0 | GPIO_Pin_1 | GPIO_Pin_2 | GPIO_Pin_3 | GPIO_Pin_4 | GPIO_Pin_5 | GPIO_Pin_6 | GPIO_Pin_7| GPIO_Pin_8 | GPIO_Pin_9 | GPIO_Pin_10 | GPIO_Pin_11;GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP; // 推挽输出⽅式GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; // 输出IO⼝最⼤最速为50MHZ GPIO_Init(GPIOC, &GPIO_InitStructure);}/******************************************************************************* 函数名称: LCD_Init** 功能描述: LCD初始化** 作者: Dream** ⽇期: 2010年12⽉06⽇*****************************************************************************/void LCD_Init(void){static uint16_t DeviceCode;//LCD_Configuration();LCD_GPIO_Config();LCD_FSMC_Config();LCD_WriteReg(0x0000,0x0001);LCD_Delay(5); // LCD_Delay 50 msDeviceCode = LCD_ReadReg(0x0000);printf(" ID=0x%x\n",DeviceCode);///////////////////////////////////LCD_Delay(5); // delay 50 msWrite_Dat(0x0023); //N=0x36 for 6.5M, 0x23 for 10M crystalWrite_Dat(0x0002);Write_Dat(0x0004);Write_Cmd(0x00E0); // PLL enableWrite_Dat(0x0001);LCD_Delay(1);Write_Cmd(0x00E0);Write_Dat(0x0003);LCD_Delay(5);Write_Cmd(0x0001); // software resetLCD_Delay(5);Write_Cmd(0x00E6); //PLL setting for PCLK, depends on resolutionWrite_Dat(0x0001);Write_Dat(0x0033);Write_Dat(0x0032);Write_Cmd(0x00B0); //LCD SPECIFICATIONWrite_Dat(0x0020);Write_Dat(0x0000);Write_Dat((HDP>>8)&0X00FF); //Set HDPWrite_Dat(HDP&0X00FF);Write_Dat((VDP>>8)&0X00FF); //Set VDPWrite_Dat(VDP&0X00FF);Write_Dat(0x0000);Write_Cmd(0x00B4); //HSYNCWrite_Dat((HT>>8)&0X00FF); //Set HTWrite_Dat(HT&0X00FF);Write_Dat((HPS>>8)&0X00FF); //Set HPSWrite_Dat(HPS&0X00FF);Write_Dat(HPW); //Set HPWWrite_Dat((LPS>>8)&0X00FF); //Set HPSWrite_Dat(LPS&0X00FF);Write_Dat(0x0000);Write_Cmd(0x00B6); //VSYNCWrite_Dat((VT>>8)&0X00FF); //Set VTWrite_Dat(VT&0X00FF);Write_Dat((VPS>>8)&0X00FF); //Set VPSWrite_Dat(VPS&0X00FF);Write_Dat(VPW); //Set VPWWrite_Dat((FPS>>8)&0X00FF); //Set FPSWrite_Dat(FPS&0X00FF);// Write_Cmd(0x00BA);// Write_Dat(0x000F); //GPIO[3:0] out 1// Write_Cmd(0x00B8);// Write_Dat(0x0007); //GPIO3=input, GPIO[2:0]=output// Write_Dat(0x0001); //GPIO0 normalWrite_Cmd(0x0036); //rotationWrite_Dat(0x0000);Write_Dat(0x0010);//============================================ //============================================ // LCD_WR_REG(0x003A); //rotation// Write_Dat(0x0050);// Write_Cmd(0x0026); //rotation// Write_Dat(0x0003);// Write_Cmd(0x0030); //rotation// Write_Dat(0x0000);//============================================= //============================================= Write_Cmd(0x00F0);//pixel data interfaceWrite_Dat(0x0003);//16位模式//Write_Cmd(0x0021);//进⼊图形颜⾊翻转模式Write_Cmd(0x00BC);//重要Write_Dat(0x0040);//对⽐度Write_Dat(0x0070);//亮度Write_Dat(0x0040);//饱和度值 //// Write_Dat(0x0080);//对⽐度// Write_Dat(0x0080);//亮度// Write_Dat(0x0080);//饱和度值 //Write_Dat(0x0001);//处理机允许Write_Cmd(0x0029); //display on//---------------------------------------------// Write_Cmd(0x0037);//重要// Write_Dat(0x000);// Write_Dat(0);LCD_Clear(WHITE);}//void WR_DATA_Prepare(void)//{// Write_Cmd(0x002c);//}/***************************************************************************** ** 函数名称: LCD_DrawPoint** 功能描述: 写⼀个点** 作者: Dream** ⽇期: 2010年12⽉06⽇*****************************************************************************/ void LCD_DrawPoint(uint16_t x, uint16_t y, uint16_t color){// LCD_SetCursor(x,y); //设置光标位置// LCD_WriteRAM_Prepare(); //开始写⼊GRAM// Write_Dat(color);u32 point = color;unsigned char rcode,gcode,bcode;rcode = (unsigned char)(point >> 16);gcode = (unsigned char)(point >> 8);bcode = (unsigned char)point;Write_Cmd(0x002A);Write_Dat(x>>8);Write_Dat(x&0x00ff);Write_Dat(479>>8);Write_Dat(479&0x00ff);Write_Cmd(0x002b);Write_Dat(y>>8);Write_Dat(y&0x00ff);Write_Dat(271>>8);Write_Dat(271&0x00ff);Write_Cmd(0x002c);Write_Dat(color);// Write_Dat((rcode << 8) | (gcode));// Write_Dat((bcode << 8) | (rcode));// Write_Dat((gcode << 8) | (bcode));}/***************************************************************************** ** 函数名称: LCD_WriteRAM_Prepare** 功能描述: 些准备** 作者: Dream** ⽇期: 2010年12⽉06⽇*****************************************************************************/ void LCD_WriteRAM_Prepare(){Write_Cmd(0x002c);}/***************************************************************************** ** 函数名称: LCD_SetCursor** 功能描述: 设置光标函数** 作者: Dream** ⽇期: 2010年12⽉06⽇*****************************************************************************/ void LCD_SetCursor(uint8_t Xpos,uint16_t Ypos){// Write_Cmd(0x002A);// Write_Dat(Xpos>>8);// Write_Dat(Xpos&0x00ff);// Write_Dat(479>>8);// Write_Dat(479&0x00ff);// Write_Cmd(0x002b);// Write_Dat(Ypos>>8);// Write_Dat(Ypos&0x00ff);// Write_Dat(271>>8);// Write_Dat(271&0x00ff);Write_Cmd(0x002A);Write_Dat(Xpos>>8);Write_Dat(Xpos&0x00ff);Write_Dat(479>>8);Write_Dat(479&0x00ff);Write_Cmd(0x002b);Write_Dat(Ypos>>8);Write_Dat(Ypos&0x00ff);Write_Dat(271>>8);Write_Dat(271&0x00ff);}/***************************************************************************** ** 函数名称: LCD_Clear** 功能描述: 清屏幕函数** 作者: Dream** ⽇期: 2010年12⽉06⽇*****************************************************************************/ //清屏函数//Color:要清屏的填充⾊void LCD_Clear(u32 color){unsigned int l=480,w;Write_Cmd(0x002a);Write_Dat(0);Write_Dat(0);Write_Dat(HDP>>8);Write_Dat(HDP&0x00ff);Write_Cmd(0x002b);Write_Dat(0);Write_Dat(0);Write_Dat(VDP>>8);Write_Dat(VDP&0x00ff);Write_Cmd(0x002c);while(l--){for(w=0;w<272;w++){Write_Dat(color);}}}/***************************************************************************** ** 函数名称: LCD_Delay** 功能描述: ⽤于LCD驱动延时** 作者: Dream** ⽇期: 2010年12⽉06⽇*****************************************************************************/ void LCD_Delay (uint32_t nCount){__IO uint16_t i;for (i=0;i}/***名称:void LCD_WindowMax()*参数:*返回:⽆*功能:设置窗⼝**/void LCD_WindowMax (unsigned int xsta,unsigned int ysta,unsigned int xend,unsigned int yend) {Write_Cmd(0X002A);Write_Dat(xsta>>8);Write_Dat(xsta&0X00FF);Write_Dat(xend>>8);Write_Dat(xend&0X00FF);Write_Cmd(0X002B);Write_Dat(ysta>>8);Write_Dat(ysta&0X00FF);Write_Dat(yend>>8);Write_Dat(yend&0X00FF);}/***名称:void LCD_Fill(uint8_t xsta, uint16_t ysta, uint8_t xend, uint16_t yend, uint16_t colour)*参数:xsta 起始X坐标ysta 起始Y坐标xend 结束X坐标yend 结束Y坐标color 待填充颜⾊*返回:⽆*功能:在指定矩形区域填充指定颜⾊,区域⼤⼩(xend-xsta)*(yend-ysta)*备注:部分区域少⼀⾏像素点**/void LCD_Fill(uint8_t xsta, uint16_t ysta, uint8_t xend, uint16_t yend, uint16_t colour){u32 n;/*设置窗⼝ */LCD_WindowMax (xsta, ysta, xend, yend);LCD_WriteRAM_Prepare(); /*开始写⼊GRAM*/n=(u32)(yend-ysta+1)*(xend-xsta+1);while(n--){Write_Dat(colour);} /*显⽰所填充的颜⾊*/}/***名称:void LCD_DrawLine(uint16_t xsta, uint16_t ysta, uint16_t xend, uint16_t yend)*参数:xsta X起始坐标ysta Y起始坐标xend X终点坐标yend Y终点坐标*返回:⽆*功能:指定坐表(两点),画线*备注:需要添加颜⾊参数**/void LCD_DrawLine(uint16_t xsta, uint16_t ysta, uint16_t xend, uint16_t yend, uint16_t color){u16 x, y, t;if((xsta==xend)&&(ysta==yend))LCD_DrawPoint(xsta, ysta, color);elseif(abs(yend-ysta)>abs(xend-xsta))/*斜率⼤于1 */{if(ysta>yend){t=ysta;yend=t;t=xsta;xsta=xend;xend=t;}for(y=ysta;y{x=(u32)(y-ysta)*(xend-xsta)/(yend-ysta)+xsta;LCD_DrawPoint(x, y, color);}}else /*斜率⼩于等于1 */{if(xsta>xend){t=ysta;ysta=yend;yend=t;t=xsta;xsta=xend;xend=t;}for(x=xsta;x<=xend;x++) /*以x轴为基准*/{y =(u32)(x-xsta)*(yend-ysta)/(xend-xsta)+ysta;LCD_DrawPoint(x, y, color);}}}/***名称:void Draw_Circle(uint16_t x0, uint16_t y0, uint8_t r)*参数:x0 中⼼点横坐标y0 中⼼点纵坐标r 半径*返回:⽆*功能:在指定位置画⼀个指定⼤⼩的圆*备注:加⼊颜⾊参数,是否填充等**/void Draw_Circle(uint16_t x0, uint16_t y0, uint8_t r, uint16_t color) {int a,b;int di;a=0;b=r;di=3-(r<<1); /*判断下个点位置的标志*/while(a<=b){LCD_DrawPoint(x0-b, y0-a, color); //3LCD_DrawPoint(x0+b, y0-a, color); //0LCD_DrawPoint(x0-a, y0+b, color); //1LCD_DrawPoint(x0-b, y0-a, color); //7LCD_DrawPoint(x0-a, y0-b, color); //2LCD_DrawPoint(x0+b, y0+a, color); //4LCD_DrawPoint(x0+a, y0-b, color); //5LCD_DrawPoint(x0+a, y0+b, color); //6LCD_DrawPoint(x0-b, y0+a, color);a++;/*使⽤Bresenham算法画圆*/if(di<0)di +=4*a+6;else{di+=10+4*(a-b);b--;}LCD_DrawPoint(x0+a, y0+b, color);}}/***名称:void LCD_DrawRectangle(uint16_t xsta, uint16_t ysta, uint16_t xend, uint16_t yend)*参数:xsta X起始坐标ysta Y起始坐标xend X结束坐标yend Y结束坐标*返回:⽆*功能:在指定区域画矩形*备注:**/void LCD_DrawRectangle(uint16_t xsta, uint16_t ysta, uint16_t xend, uint16_t yend, uint16_t color) {LCD_DrawLine(xsta, ysta, xend, ysta, color);LCD_DrawLine(xsta, ysta, xsta, yend, color);LCD_DrawLine(xsta, yend, xend, yend, color);LCD_DrawLine(xend, ysta, xend, yend, color);}/***名称:void LCD_ShowChar(u8 x, u16 y, u8 num, u8 size, u16 PenColor, u16 BackColor)*参数:x,y 起始坐标(x:0~234 y:0~308)num 字符ASCII码值size字符⼤⼩,使⽤默认8*16PenColor 字体颜⾊BackColor 字体背景颜⾊*功能:*备注:注意屏幕⼤⼩**/void LCD_ShowChar(u8 x, u16 y, u8 num, u8 size, u16 PenColor, u16 BackColor){#define MAX_CHAR_POSX 232#define MAX_CHAR_POSY 304u8 temp;u8 pos,t;if(x>MAX_CHAR_POSX||y>MAX_CHAR_POSY)return;num=num-' '; /*得到偏移后的值 */for(pos=0;pos{temp=asc2_1608[num][pos]; /*调⽤1608字体 */for(t=0;t{if(temp&0x01) /*从低位开始*/{LCD_DrawPoint(x+t, y+pos, PenColor); /*画字体颜⾊⼀个点*/}elseLCD_DrawPoint(x+t, y+pos, BackColor); /*画背景颜⾊⼀个点*/temp>>=1;}}}//m^n函数u32 mypow(u8 m,u8 n){u32 result=1;while(n--)result*=m;return result;}//显⽰2个数字//x,y :起点坐标//len :数字的位数//size:字体⼤⼩//color:颜⾊//num:数值(0~4294967295);void LCD_ShowNum(u8 x,u8 y,u32 num,u8 len, u16 PenColor, u16 BackColor){u8 size = 16; /* 这⾥使⽤默认的16*8 */u8 t,temp;u8 enshow=0;for(t=0;t{temp=(num/mypow(10,len-t-1))%10;if(enshow==0&&t<(len-1)){if(temp==0){LCD_ShowChar(x+(size/2)*t,y,' ',size, PenColor, BackColor);continue;}else enshow=1;}LCD_ShowChar(x+(size/2)*t,y,temp+'0',size, PenColor, BackColor);}}/**名称:void LCD_ShowCharString(uint16_t x, uint16_t y, const uint8_t *p, uint16_t PenColor, uint16_t BackColor)参数:x,y 起始坐标p 指向字符串起始地址PenColor 字符颜⾊BackColor 背景颜⾊功能:备注:⽤16字体,可以调节此函数不能单独调⽤**/void LCD_ShowCharString(uint16_t x, uint16_t y, const uint8_t *p, uint16_t PenColor, uint16_t BackColor){uint8_t size = 16; /*---字符⼤⼩默认16*8---*/if(x>MAX_CHAR_POSX){x=0;y+=size;} /*超出X轴字体最⼩单位,换⾏*/if(y>MAX_CHAR_POSY){y=x=0;LCD_Clear(WHITE);} /*超出Y轴字体最⼩单位,回到原点,并且清屏*/LCD_ShowChar(x, y, *p, size, PenColor, BackColor); /*0表⽰⾮叠加⽅式*/}/***名称: u16 findHzIndex(u8 *hz)*参数:hz*功能:索引汉字存储的内存地址*备注:**/u16 findHzIndex(u8 *hz) /* 在⾃定义汉字库在查找所要显⽰ *//* 的汉字的位置 */{u16 i=0;FNT_GB16 *ptGb16 = (FNT_GB16 *)GBHZ_16; /*ptGb16指向GBHZ_16*/while(ptGb16[i].Index[0] > 0x80){if ((*hz == ptGb16[i].Index[0]) && (*(hz+1) == ptGb16[i].Index[1])) /*汉字⽤两位来表⽰地址码*/{return i;}i++;if(i > (sizeof((FNT_GB16 *)GBHZ_16) / sizeof(FNT_GB16) - 1)) /* 搜索下标约束 */{break;}}return 0;}/***名称:void WriteOneHz(uint16_t x0, uint16_t y0, uint8_t *pucMsk, uint16_t PenColor, uint16_t BackColor) *参数:x0,y0 起始坐标*pucMsk 指向PenColor 字符颜⾊BackColor 背景颜⾊*功能:*备注:此函数不能单独作为汉字字符显⽰**/void WriteOneHz(u16 x0, u16 y0, u8 *pucMsk, u16 PenColor, u16 BackColor){u16 i,j;u16 mod[16]; /* 当前字模 16*16 */u16 *pusMsk; /* 当前字库地址 */u16 y;pusMsk = (u16 *)pucMsk;for(i=0; i<16; i++) /* 保存当前汉字点阵式字模 */{mod[i] = *pusMsk; /* 取得当前字模,半字对齐访问 */mod[i] = ((mod[i] & 0xff00) >> 8) | ((mod[i] & 0x00ff) << 8);/* 字模交换⾼低字节*/pusMsk = pusMsk+1;}y = y0;for(i=0; i<16; i++) /* 16⾏ */{for(j=0; j<16; j++) /* 16列 */{if((mod[i] << j) & 0x8000) /* 显⽰第i⾏共16个点 */{LCD_DrawPoint(x0+j, y0+i, PenColor);}else{LCD_DrawPoint(x0+j, y0+i, BackColor);}}y++;}}/***名称:void LCD_ShowHzString(u16 x0, u16 y0, u8 *pcStr, u16 PenColor, u16 BackColor)*参数:x0,y0 起始坐标pcStr 指向PenColor 字体颜⾊BackColor 字体背景*功能:显⽰汉字字符串*备注:这个函数不能单独调⽤**/void LCD_ShowHzString(u16 x0, u16 y0, u8 *pcStr, u16 PenColor, u16 BackColor){#define MAX_HZ_POSX 224#define MAX_HZ_POSY 304u16 usIndex;u8 size = 16;FNT_GB16 *ptGb16 = 0;ptGb16 = (FNT_GB16 *)GBHZ_16;if(x0>MAX_HZ_POSX){x0=0;y0+=size;} /*超出X轴字体最⼩单位,换⾏*/if(y0>MAX_HZ_POSY){y0=x0=0;LCD_Clear(WHITE);} /*超出Y轴字体最⼩单位,回到原点,并且清屏*/ usIndex = findHzIndex(pcStr);WriteOneHz(x0, y0, (u8 *)&(ptGb16[usIndex].Msk[0]), PenColor, BackColor); /* 显⽰字符 */}/***名称:void LCD_ShowString(u16 x0, u16 y0, u8 *pcstr, u16 PenColor, u16 BackColor)*参数:x0 y0 起始坐标pcstr 字符串指针PenColor 字体颜⾊BackColor 字体背景⾊*功能:调⽤字符和汉字显⽰函数,实现字符串显⽰*备注:**/void LCD_ShowString(u16 x0, u16 y0, u8 *pcStr, u16 PenColor, u16 BackColor){while(*pcStr!='\0'){if(*pcStr>0x80) /*显⽰汉字*/{LCD_ShowHzString(x0, y0, pcStr, PenColor, BackColor);pcStr += 2;x0 += 16;}else /*显⽰字符*/{LCD_ShowCharString(x0, y0, pcStr, PenColor, BackColor);pcStr +=1;x0+= 8;}}}/***************************************************************************** 名称:u16 ili9320_BGRtoRGB(u16 Color)* 功能:RRRRRGGGGGGBBBBB 改为 BBBBBGGGGGGRRRRR 格式* ⼊⼝参数:Color BRG 颜⾊值* 出⼝参数:RGB 颜⾊值* 说明:内部函数调⽤* 调⽤⽅法:****************************************************************************/u16 LCD_RGBtoBGR(u16 Color){u16 r, g, b, bgr;b = (Color>>0) & 0x1f; /* 提取B */g = (Color>>5) & 0x3f; /* 中间六位 */r = (Color>>11) & 0x1f; /* 提取R */bgr = (b<<11) + (g<<5) + (r<<0);return( bgr );}/***************************************************************************** 名称:void LCD_DrawPicture(u16 StartX,u16 StartY,u16 EndX,u16 EndY,u16 *pic) * 功能:在指定座标范围显⽰⼀副图⽚* ⼊⼝参数:StartX ⾏起始座标* StartY 列起始座标* EndX ⾏结束座标* EndY 列结束座标pic 图⽚头指针* 出⼝参数:⽆* 说明:图⽚取模格式为⽔平扫描,16位颜⾊模式* 调⽤⽅法:LCD_DrawPicture(0,0,100,100,(u16*)demo);****************************************************************************/void LCD_DrawPicture(u16 StartX,u16 StartY,u16 Xend,u16 Yend,u8 *pic){static u16 i=0,j=0;u16 *bitmap = (u16 *)pic;for(j=0; j{for(i=0; iLCD_DrawPoint(StartX+i, StartY+j, *bitmap++);}}//快速ALPHA BLENDING算法.//src:源颜⾊//dst:⽬标颜⾊//alpha:透明程度(0~32)//返回值:混合后的颜⾊.u16 gui_alpha_blend565(u16 src,u16 dst,u8 alpha){u32 src2;u32 dst2;//Convert to 32bit |-----GGGGGG-----RRRRR------BBBBB|src2=((src<<16)|src)&0x07E0F81F;dst2=((dst<<16)|dst)&0x07E0F81F;//Perform blending R:G:B with alpha in range 0..32//Note that the reason that alpha may not exceed 32 is that there are only//5bits of space between each R:G:B value, any higher value will overflow//into the next component and deliver ugly result.dst2=((((dst2-src2)*alpha)>>5)+src2)&0x07E0F81F;return (dst2>>16)|dst2;}。