零死角玩转stm32-高级篇5、3.2寸液晶显示(中英文+图片)
stm32 TFT液晶

Stm32的TFT LCD显示器控制学习笔记学习stm32,TFT LCD显示屏控制是很重要的一章,本人在初步学习STM32遇到了很多困难,所以把学习中积累的部分感觉重要的知识点罗列出来。
目前常用的TFT液晶内部驱动芯片是ILI9320,ILI9325系列,内部原理基本一致,我用的是ILI9320。
用stm32驱动液晶,实际上就是驱动ILI9320芯片。
点亮TFT LCD的具体步骤有:(1)stm32与ILI9320芯片管脚的初始化。
void LCD_Init(void); /*初始化LCD,也就是初始化LCD控制器ILI9320芯片与stm32控制器的管脚连接配置*/其中包括CS:TFTLCD片选信号,WR:向TFTLCD写入信号,RD:从TFTLCD读取信号,DB(15--0):16位双向数据线,RST:硬复位TFTLCD,RS:命令/数据标志(0 读写命令;1 读写数据),TFT模块有个控制器,名为ILI9320,该控制器自带显存,其显存总大小为172820,模块数据线与显存的对应关系位565方式SGRAM (Synchronous Graphics Random-Access Memory),同步图形随机存储器,是一种专为显卡设计的显存、一种图形读写能力较强的显存,由SDRAM改良而成。
SGRAM 读写数据时不是一一读取,而是以“块”(Block)为单位,从而减少了内存整体读写的次数,提高了图形控制器的效率。
同SDRAM一样,SGRAM也分普通SGRAM与DDR SGRAM 两种。
R0,这个命令有两个功能,如果对它写,则最低位位OSC,用于开启或关闭振荡器,而如果对它读,返回控制器型号。
我们知道了控制器型号,可以针对不同型号的控制器,进行不同对的初始化。
R3,入口模式命令。
重点关注I/D0,I/D1,AM这三个位,因为这3个位控制了屏幕的显示方向。
AM:控制GRAM更新方向,当AM=0的时候,地址以行方向更新,当为1的时候,地址以列方向更新。
STM32通用定时器(TIM2-5)基本用法

if(TIM_GetITStatus(TIM3 , TIM_IT_Update) == SET) { TIM_ClearITPendingBit(TIM3 , TIM_FLAG_Update); if(GPIO_ReadOutputDataBit(GPIOA,GPIO_Pin_8)) GPIO_ResetBits(GPIOA, GPIO_Pin_8); else GPIO_SetBits(GPIOA, GPIO_Pin_8); } } //注意使能定时器时钟
void TIMER3_Init() { TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure; TIM_DeInit(TIM3); RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE); TIM_TimeBaseStructure.TIM_Period=10000;//ARR 的值 TIM_TimeBaseStructure.TIM_Prescaler=7200-1; TIM_TimeBaseStructure.TIM_CounterMode=TIM_CounterMode_Up; //向上计数模式 TIM_TimeBaseInit(TIM3, &TIM_TimeBaseStructure); TIM_ITConfig(TIM3,TIM_IT_Update,ENABLE); TIM_Cmd(TIM3, ENABLE); //开启时钟 }
STM32显示汉字精讲

STM32显示汉字精讲本文是一个自学者的学习心得,通过大白话解释写代码,欢迎指教。
主要应用目的是在TFT屏幕上显示汉字,FAT32文件系统的SD卡存储16*16的汉字库,汉字显示是通过查找字库方法。
主要应用几个高级文件:1.GUI 屏幕显示函数库2.FATFS应用在单片机,ARM文件系统库3.TFT,SD卡驱动致力于应用,所以对于原理就不要深究了,我们把接口函数研究明白就行了!对于以上GUI和FATFS高级文件,我们看文档都很多,也很长,如果想速成的话(不建议速成,时间够的话,知识要一步一个脚印的学,要把原理学好,为以后省去很多麻烦),简单学习方法:1.先把接口函数里的对应数据类型记住,特别是结构体,因为我们应用就是直接或间接改这些参数2.学习接口函数原型,这部分主要包括:函数返回值,参数还有函数实现的功能,再就是函数应用条件,有例子最好看一下例子怎么使用函数对于这些大量文档把这两点把握好,就可以对随意使用了,当然这里是建立在文件移植好之后。
STM32的显示汉字几处关键程序跟大家分享一下:FATFS fs;FIL fsrc; /* file objects */UINT br; // File R/W countstatic uint8_t Find_Chinese(uint8_t* str, uint8_t* p) //字库中索引对应的汉字{uint8_t High8bit,Low8bit; //字库存储是一个字节8位的,而屏幕是16位传送的,所以把两个字节合并成一个16位数,与屏幕驱动相匹配,这里要注意数据的大小端问题FRESULT res;uint8_t error[]="Please put the sys folder which include the font file HZK16.bin into the SD card root directory. ";High8bit=*str; /* ?高八位数据*/Low8bit=*(str+1); /* 低八位数据*/f_mount(0, &fs); //fatfs申请一个工作区/* Infinite loop */res = f_open(&fsrc, "/sys/HZK16.bin", FA_OPEN_EXISTING | FA_READ); /* 打开SD卡里的字库*/if(res != 0){LCD_ShowString(32,100,error,RED ,BLACK ); //在指定位置显示errorreturn 1;}f_lseek(&fsrc,32*((High8bit-0xa0-1)*94+(Low8bit-0xa0-1))); //根据公式算出对应汉字在字库中首地址f_read(&fsrc, p, 32, &br); //取出这个汉字的字模16*16/8=32个字节,所以取32字节放在p里f_close(&fsrc); //用完关闭文件f_mount(0, NULL); //注销工作区return 0;}*************************************************************** **************** **/void PutChinese(u16 x, u16 y, u8 *c, u32 PenColor, u32 BackColor){u16 i=0;u16 j=0;u8 buffer[32];u16 tmp_char=0;if(!Find_Chinese(c,buffer)) //判断字库里是否有对应的汉字{LCD_WindowMax(x,y,x+16,y+16); /*设置窗口*/LCD_SetCursor(x,y); /*设置当前坐标*/LCD_WriteRAM_Prepare(); //LCD驱动函数里的,准备写数据/* LCD驱动写是一次写两个字节,32字节发送16次就把一个汉字显示出来*/for (i=0;i<16;i++){tmp_char=buffer[i*2];tmp_char=(tmp_char<<8);tmp_char|=buffer[2*i+1]; /*把16位数据存入tem_char*/for (j=0;j<16;j++) //这里16表示16位数据一位一位绘制屏幕上的点{if((tmp_char<<="" p="">LCD_WriteRAM(PenColor);elseLCD_WriteRAM(BackColor);}}LCD_WindowMax(0x00,0x00,240,320); /*恢复窗口*/}*************************************************************** **************** **/void GUI_Put(u16 x, u16 y, u8 *str,u32 PenColor, u32BackColor){do{if (x>MAX_HZ_POSX) /*保证空间能放下16*16字体,否则换行*/{y+=16;x=0;}if (y>MAX_HZ_POSY) /*保证空间能放下16*16字体,否则换行*/{y=0;}if ( *str < 0x80) /* 字符是16*8的*/{LCD_ShowCharString(x, y, str, PenColor, BackColor);x+= 8;str++;}else /*′显示汉字*/{PutChinese(x, y, str++, PenColor, BackColor);str++;x+=16;}}while(*str!=0);}。
STM32的液晶与触摸屏显示

STM32的液晶与触摸屏显示TFT-LCD 英文全称为:Thim Film Transistor Liquid Crystal Display。
TFT即薄膜场效应管。
所谓薄膜晶体管,是指液晶显示器上的每一液晶像素点都是由集成在其后的薄膜晶体管来驱动。
从而可以做到高速度、高亮度、高对比度显示屏幕信息。
TFT-LCD 液晶显示屏是薄膜晶体管型液晶显示屏。
我们采用的3.5 寸液晶屏,它的控制芯片是ILI9488,触摸驱动芯片为TSC2046。
最大支持解析度为:HVGA,分辨率为480×320,接口可以为8位或者16位并口,我们这里是使用16 位并口,以发挥STM32的优势。
而背光则使用一个三极管驱动。
引脚电路图如下图:引脚介绍LCD_CS是TFTLCD的片选信号LCD_RS是命令和数据的标志(0,读写命令。
1是写命令)LCD_WR是向TFTLCD写入数据LCD_RD是从TFTLCD读取数据D[17-1]是数据16位双向数据线RST是硬复位的标志BL_CTR背光处理信号lT_MISO/T_MOSI/T_PEN/T_CS/T_CLK,触摸屏接口信号驱动时序图:驱动流程:RGB565格式说明(16色):指令集:0XD3指令:用于读取LCD控制器的ID0X36指令:用于控制读写方向0X2A指令:用于设置横坐标起始位置和终止位置(x坐标)0X2B指令:用于设置纵坐标起始位置和终止位置(y坐标)0X2C指令:用于写颜色数据0X2E指令:用于读颜色指令接线图:程序:#include "led.h"#include "delay.h"#include "sys.h"#include "usart.h"#include "lcd.h"int main(void){u8 x=0;u8 lcd_id[12]; //存放LCD ID字符串delay_init(); //延时函数初始化uart_init(9600); //串口初始化为9600LED_Init(); //初始化与LED连接的硬件接口LCD_Init();POINT_COLOR=RED;sprintf((char*)lcd_id,"LCD ID:%04X",lcddev.id);//将LCD ID打印到lcd_id数组。
STM32入门教程

1. 51 系统结构
51 系统结构框图
第 2 页 共 53 页
《零死角玩转 STM32》— F1 系列
图 1 51 系统结构框图 我们说的 51 一般是指 51 系列的单片机,型号有很多,常见的有 STC89C51、 AT89S51,其中国内用的最多的是 STC89C51/2,下面我们就以 STC89C51 来讲解,并以 51 简称。
第 1 页 共 53 页
《零死角玩转 STM32》— F1 系列
第 1 章 一天入门 STM32
本章参考资料:《STM32 中文参考手册》 《CM3 权威指南 CnR2》 学习本章时,配合《STM32 中文参考手册》GPIO 章节一起阅读,效果会更佳,特 别是涉及到寄存器说明的部分。
1.1 51 与 STM32 简介
I-Code 用于取指,D-Code 用于查表等操作,它们按最佳执行速度进行优化。 系统总线(System)用于访问内存和外设,覆盖的区域包括 SRAM,片上外设,片外 RAM,片外扩展设备,以及系统级存储区的部分空间。 私有外设总线负责一部分私有外设的访问,主要就是访问调试组件。它们也在系统级 存储区。 还有一个 MDA 总线,从字面上看,DMA 是 data memory access 的意思,是一种连接 内核和外设的桥梁,它可以访问外设、内存,传输不受 CPU 的控制,并且是双向通信。简 而言之,这个家伙就是一个速度很快的且不受老大控制的数据搬运工,这个在 51 里面是没 有的。
1.2 学习方法的区别
学习 51 用寄存器,学习 STM32 用库。 以前我们在学习 51 的时候,用的是寄存器编程的方法,想要实现什么效果,直接往寄 存器里面赋值,优点是直观,简单粗暴,知道自己具体干了啥,心里踏实。 直接操作寄存器之所以在 51 上可行,究其原因,我想有两点: 1、51 主频不高,资源有限,必须注重程序执行的效率,只能直接操作寄存器。关键 的地方还得用汇编,不适合用固件库。
零死角玩转stm32-高级篇4、FSMC详解(3.2寸液晶触摸画板)

0、友情提示《零死角玩转STM32》系列教程由初级篇、中级篇、高级篇、系统篇、四个部分组成,根据野火STM32开发板旧版教程升级而来,且经过重新深入编写,重新排版,更适合初学者,步步为营,从入门到精通,从裸奔到系统,让您零死角玩转STM32。
M3的世界,与野火同行,乐意惬无边。
另外,野火团队历时一年精心打造的《STM32库开发实战指南》将于今年10月份由机械工业出版社出版,该书的排版更适于纸质书本阅读以及更有利于查阅资料。
内容上会给你带来更多的惊喜。
是一本学习STM32必备的工具书。
敬请期待!4、液晶触摸画板4.1实验简介本实验向大家介绍如何使用STM32的FSMC接口驱动LCD屏,及使用触摸屏控制器检测触点坐标。
4.2 LCD控制器简介LCD,即液晶显示器,因为其功耗低、体积小,承载的信息量大,因而被广泛用于信息输出、与用户进行交互,目前仍是各种电子显示设备的主流。
因为STM32内部没有集成专用的液晶屏和触摸屏的控制接口,所以在显示面板中应自带含有这些驱动芯片的驱动电路(液晶屏和触摸屏的驱动电路是独立的),STM32芯片通过驱动芯片来控制液晶屏和触摸屏。
以野火3.2寸液晶屏(240*320)为例,它使用ILI9341芯片控制液晶屏,通过TSC2046芯片控制触摸屏。
4.2.1 ILI9341控制器结构液晶屏的控制芯片内部结构非常复杂,见错误!未找到引用源。
最主要的是位于中间GRAM(Graphics RAM),可以理解为显存。
GRAM中每个存储单元都对应着液晶面板的一个像素点。
它右侧的各种模块共同作用把GRAM存储单元的数据转化成液晶面板的控制信号,使像素点呈现特定的颜色,而像素点组合起来则成为一幅完整的图像。
框图的左上角为ILI9341的主要控制信号线和配置引脚,根据其不同状态设置可以使芯片工作在不同的模式,如每个像素点的位数是6、16还是18位;使用SPI接口还是8080接口与MCU进行通讯;使用8080接口的哪种模式。
战舰STM32F103开发版LCD显示实验和触摸屏实验文档

接下来看指令:0X36,这是存储访问控制指令,可以控制 ILI9341 存储器的读写方向,简 单的说,就是在连续写 GRAM 的时候,可以控制 GRAM 指针的增长方向,从而控制显示方式 (读 GRAM 也是一样) 。该指令如表 18.1.1.2 所示: 顺序 指令 参数 控制 RS 0 1 RD 1 1 WR ↑ ↑ D15~D8 XX XX D7 0 MY D6 0 MX 各位描述 D5 1 MV D4 1 ML D3 0 BGR D2 1 MH D1 1 0 D0 0 0 HEX 36H 0
RS:命令/数据标志(0,读写命令;1,读写数据) 。 80 并口在上一节我们已经有详细的介绍了, 这里我们就不再介绍, 需要说明的是, TFTLCD 模块的 RST 信号线是直接接到 STM32 的复位脚上,并不由软件控制,这样可以省下来一个 IO 口。另外我们还需要一个背光控制线来控制 TFTLCD 的背光。所以,我们总共需要的 IO 口数 目为 21 个。这里还需要注意,我们标注的 DB1~DB8,DB10~DB17,是相对于 LCD 控制 IC 标 注的,实际上大家可以把他们就等同于 D0~D15,这样理解起来就比较简单一点。 ALIENTEK 提供 2.8/3.5/4.3/7 寸等不同尺寸的 TFTLCD 模块,其驱动芯片有很多种类型, 比如有:ILI9341/ILI9325/RM68042/RM68021/ILI9320/ILI9328/LGDP4531/LGDP4535/SPFD5408 /SSD1289/1505/B505/C505/NT35310/NT35510 等(具体的型号, 大家可以通过下载本章实验代码, 通过串口或者 LCD 显示查看),这里我们仅以 ILI9341 控制器为例进行介绍,其他的控制基本 都类似,我们就不详细阐述了。 ILI9341 液晶控制器自带显存,其显存总大小为 172800(240*320*18/8) ,即 18 位模式(26 万色)下的显存量。在 16 位模式下,ILI9341 采用 RGB565 格式存储颜色数据,此时 ILI9341 的 18 位数据线与 MCU 的 16 位数据线以及 LCD GRAM 的对应关系如图 18.1.1.4 所示:
3.2寸TFT液晶屏,

3.2⼨TFT液晶屏, 16:9 WQVGA 44pin3.2⼨TFT液晶屏, 16:9 WQVGA 44pin产品图⽚产品名称 3.2⼨TFT液晶屏外观尺⼨ 47.6*80.9*2.3mm显⽰尺⼨ 41.76*69.6mm驱动IC ST7793/HX8352-A接⼝类型 MCU 并⼝ 44pin 焊脚 16bit背光类型 5*LED 并联电压:2.8--3.3V功耗 1 Wpin脚间距 0.8mm分辨率 240*400触摸可选详细资料参阅规格书pin脚定义:管脚号符号功能1GND地2YD触摸屏信号线3 XR触摸屏信号线4YU触摸屏信号线5XL触摸屏信号线6GND地7 NC悬空8 NC悬空9FMARK LCM帧同步脉冲10NC悬空11NC悬空12RESET复位信号线13NC悬空14NC悬空15DB15LCD数据信号线16DB14LCD数据信号线17DB13LCD数据信号线18DB12LCD数据信号线19DB11LCD数据信号线20DB10LCD数据信号线21DB9LCD数据信号线22DB8LCD数据信号线23DB7LCD数据信号线24DB6LCD数据信号线25DB5LCD数据信号线26DB4LCD数据信号线27DB3LCD数据信号线28DB2LCD数据信号线29DB1LCD数据信号线30DB0LCD数据信号线31RD读信号,低有效32WR写信号,低有效33RS指令/数据选择端,L:指令,H:数据 34CS⽚选信号,低有效35GND地36IOVCC I/O接⼝电压37VCC模拟电路电源38LEDK5背光LED负极性端39LEDK4背光LED负极性端40LEDK3背光LED负极性端41LEDK2背光LED负极性端42LEDK1背光LED负极性端43LEDA背光LED正极性端44GND地。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
0、友情提示《零死角玩转STM32》系列教程由初级篇、中级篇、高级篇、系统篇、四个部分组成,根据野火STM32开发板旧版教程升级而来,且经过重新深入编写,重新排版,更适合初学者,步步为营,从入门到精通,从裸奔到系统,让您零死角玩转STM32。
M3的世界,与野火同行,乐意惬无边。
另外,野火团队历时一年精心打造的《STM32库开发实战指南》将于今年10月份由机械工业出版社出版,该书的排版更适于纸质书本阅读以及更有利于查阅资料。
内容上会给你带来更多的惊喜。
是一本学习STM32必备的工具书。
敬请期待!5、液晶显示(中、英、Pic )5.1 实验简介在《液晶触摸画板》中,我们已经成功地实现了驱动LCD 和触摸屏,并制作了触摸画板小应用,但是若要显示文字或图片文件,则还需要利用文件系统,读取保存在SD 卡中的字库文件、图片文件。
5.2 什么是字模我们知道其实液晶屏就是一个由像素点组成的点阵,若要显示文字,则需要很多像素点的共同构成。
见下错误!未找到引用源。
,图中是两个由16*16的点阵显示的两个汉字。
如果我们规定:每个汉字都由这样16*16的点阵来显示,把笔迹经过的像素点以“1”表示,没有笔迹的点以“0”表示,每个像素点的状态以一个二进制位来记录,用16*16/8 =32个字节就可以把这个字记录下来。
这32个字节数据就称为该文字的字模,还有其它常用字模是24*24、32*32的。
16*16的“字”的字模数据为:1./* 字 */2. unsigned char code Bmp003[]=3. {4. /*------------------------------------------------------------5. ; 源文件 / 文字 : 字6. ; 宽×高(像素): 16×167. ; 字模格式/大小 : 单色点阵液晶字模,横向取模,字节正序/32字节8. ----------------------------------------------------------*/ 9.Bit7 ~Bit0B it7 ~Bit0 每个字16x2Byte10.0x02,0x00,0x01,0x00,0x3F,0xFC,0x20,0x04,0x40,0x08,0x1F,0xE0,0x00,0x40,0x00,0x80,11.0xFF,0xFF,0x7F,0xFE,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x05,0x00,0x02,0x00,12.};在这样的字模中,以两个字节表示一行像素点,16行构成一个字模。
如果使用LCD的画点函数,按位来扫描这些字模数据,把为1的位以黑色来显示(也可以使用其它颜色),即可把整个点阵还原出来,显示在液晶屏上。
5.3 制作字模我们采用“字模III-增强版v3.91”软件来制作中文字库,步骤如下:1.打开字模软件2.点击“自动批量生成字库”按钮选项。
软件界面左下角将出现一下几个按钮选项:3.点击选择“二级汉字库”按钮。
在“输入批量字符”框里面将会列出二级汉字的所有汉字,其中共收录了6768个汉字字符,非特殊情况下都能够满足大家的要求,如图:4.点击“字库智能生成”按钮,弹出“字库批量参数确认”对话框。
我们在“源字体”选项里面做如下设置,需要注意的是大小问题,因为我们本次的设计目标是实现16*16的汉字,所以在此选择’小四’字体。
设置好之后如下:5.点击“开始转换进程”按钮.就会在安装目录下或者你设置好的目录下生成.c后缀的字库文件。
6.对于LCD显示来说,只要能够在指定的位置描写制定颜色的点,那么就能够很好地根据汉字字模信息来描写汉字。
在此,为了能够更好的清楚字模的取向和高低位的排列顺序,我们可以现先在pc测试我们刚才制作好的库文件。
在这里我们取“当”字符的数据来测试。
VC6.0测试源码如下,该代码实现了把字模中为1的点都用数字“8”来表示:1.#include <stdio.h>2.3.unsigned char cc[] =4.{/*"当"字符*/5.0x00,0x80,0x10,0x90,0x08,0x98,0x0C,0x90,0x08,0xA0,0x00,0x80,0x3F,0xFC,0x00,0x04,6.0x00,0x04,0x1F,0xFC,0x00,0x04,0x00,0x04,0x00,0x04,0x3F,0xFC,0x00,0x04,0x00,0x007.};8.9.void main()10.{11.int i,j;12. unsigned char kk;13.for ( i=0; i<16; i++)14. {15.for(j=0; j<8; j++)16. {17. kk = cc[2*i] << j ; //左移J位18.19.if( kk & 0x80) //如果最高位为120. {21. printf("8");22. }23.else24. {25. printf(" ");26. }27. }28.29.for(j=0; j<8; j++)30. {31.32. kk = cc[2*i+1] << j ; //左移J位33.34.if( kk & 0x80) //如果最高位为135. {36. printf("8");37. }38.else39. {40. printf(" ");41. }42.43. }44.45. printf("\n");46.47. }48. printf("\n\n");49.50.}51.52.测试结果如下:看到以上的测试结果,相信大家对汉字的取模方向和高低位的排列顺序有了比较直观的了解。
7.回到“字模III-增强版v3.91”软件,采用与之前同样的方式生成bin格式的字库文件(即“生成格式”选项设置为“bin文件格式”)。
在软件安装目录下会生成Font.dat文件,我们用“WinHex”软件查看他的具体内容,与刚才制作的.c字库的文件内容是一致的,对比如下:将生成的汉字字库拷贝到SD卡根目录下并重命名为“HZLIB.bin”。
把该文件保存到SD卡中,STM32芯片通过文件系统读取文件即可获得字库的数据。
5.4. BMP图片格式使用LCD屏来显示BMP图片,就如同播放MP3文件一样,首先要了解其文件的格式。
BMP文件格式,又称为位图(Bitmap)或是DIB(Device-Independent Device,设备无关位图),是Windows系统中广泛使用的图像文件格式。
BMP 文件保存了一幅图像中所有的像素。
BMP格式可以保存单色位图、16色或256色索引模式像素图、24位真彩色图象,每种模式中单一像素点的大小分别为1/8字节,1/2字节,1字节和32字节。
目前最常见的是256位色BMP和24位色BMP。
BMP文件格式还定义了像素保存的几种方法,包括不压缩、RLE压缩等。
常见的BMP文件大多是不压缩的。
Windows所使用的BMP文件,在开始处有一个文件头,大小为54字节。
保存了包括文件格式标识、颜色数、图像大小、压缩方式等信息,因为我们仅讨论24位色不压缩的BMP,所以文件头中的信息基本不需要注意,只有“大小”这一项对我们比较有用。
图像的宽度和高度都是一个32位整数,在文件中的地址分别为0x0012和0x0016。
54个字节以后,如果是16色或256色BMP,则还有一个颜色表,但在24位色BMP文件则没有,我们这里不考虑。
接下来就是实际的像素数据了。
因此总的来说BMP图片的优点是简单。
5.4.1 BMP图片分析下面来用WinHex软件(跟UltraEdit软件功能类似)来分析一下BMP图像的文件内容:测试图片为123.bmp,先用ACDSee软件打开,查看图像,其图像内容见图 0-1。
图 0-1 测试图片可知,这幅图像的大小是15*8,是24位真彩色bmp图像。
接着使用WinHex软件打开,可读取到该文件的原始数据见图 0-2。
图 0-2 测试图片的原始数据1.文件头部信息部分(前面54字节)图 0-3 文件头部信息图 0-3,阴影部分是文件头部信息。
它可以分为两块:BMP文件头和位图信息头。
0~1字节BMP文件的 0和1字节用于表示文件的类型。
如果是位图文件类型,必须分别为0x42 和0x4D ,0x424D=’BM’。
3~14字节3到14字节的意义可以用一个结构体来描述。
如下:1.typedef struct tagBITMAPFILEHEADER2.{3.//attention: sizeof(DWORD)=4 sizeof(WORD)=24. DWORD bfSize; //文件大小5. WORD bfReserved1; //保留字,不考虑6. WORD bfReserved2; //保留字,同上7. DWORD bfOffBits; //实际位图数据的偏移字节数,即前三个部分长度之和8.} BITMAPFILEHEADER,tagBITMAPFILEHEADER;14~53字节头部信息剩下的部分就是位图信息头,14到53字节内容的意义如下:1.typedef struct tagBITMAPINFOHEADER2.{3.//attention: sizeof(DWORD)=4 sizeof(WORD)=24.DWORD biSize; //指定此结构体的长度,为405.LONG biWidth; //位图宽,说明本图的宽度,以像素为单位6.LONG biHeight; //位图高,指明本图的高度,像素为单位7.WORD biPlanes; //平面数,为18.WORD biBitCount; //采用颜色位数,可以是1,2,4,8,16,24新的可以是329.DWORD biCompression; //压缩方式,可以是0,1,2,其中0表示不压缩10.DWORD biSizeImage; //实际位图数据占用的字节数11.LONG biXPelsPerMeter; //X方向分辨率12.LONG biYPelsPerMeter; //Y方向分辨率13.DWORD biClrUsed; //使用的颜色数,如果为0,则表示默认值(2^颜色位数)14.DWORD biClrImportant; //重要颜色数,如果为0,则表示所有颜色都是重要的15.16.} BITMAPINFOHEADER,tagBITMAPINFOHEADER;由上述分析与WinHex软件的分析内容结合得到该图片的信息如下:文件大小:438保留字:0保留字:0实际位图数据的偏移字节数:54位图信息头:结构体的长度:40位图宽:15位图高:8biPlanes平面数:1biBitCount采用颜色位数:24压缩方式:0biSizeImage实际位图数据占用的字节数:0X方向分辨率:3780Y方向分辨率:3780使用的颜色数:0重要颜色数:02.图像像素数据部分(如果是24位真彩色,则54字节之后就是像素部分):图 0-4 图像像素数据有些读者可能已经发现,在像素部分夹杂着一些值为0的数据信息,如下图灰色部分所示:本例子中整张图片都是灰色的,为什么会有0像素的出现呢?对齐的数据,更容易被操作系统或者硬件调入cache,使得cache的命中率提高,从而提高访问效率。