目录
字符编码
由于计算机只能识别0和1,文字也只能以0和1的形式在计算机里存储,所以我们需要对文字进行编码才能让计算机处理,编码的过程就是规定特定的01数字字符串来表示特定的文字,最简单的字符编码就是ASCII编码。
ASCII编码
学习C语言的时候,我们知道在程序设计中使用的ASCII编码表约定了一些控制字符、英文及数字。他们在存储器中,本质也是二进制数,只是我们约定这些二进制数可以表示某些特殊意义,如以ASCII编码解释数字“0x41”时,它表示的是英文字符“A”。ASCII编码表可以分为两部分,第一部分是控制字符或通讯专用字符,它们的数字编码从0-31,它们并没有特定的图形显示,但会根据不同的应用程序,而对文本显示有不同的影响.ASCII表的第二部分包括空格、阿拉伯数字、标点符号、大小写英文字符以及“DEL”,这部分的数字编码从32-127,除了最后一个DEL符号外都能以图形的方式显示,具体的ASCII表这里不再赘述,读者可以网上查找。
后来,计算机推广之后,还加入了各种形状和符号,一直编号到255,从128-255的字符被称为ASCII的扩展字符集,至此,基本存储单位Byte能表示的编号已经全部用完了。
中文编码
由于汉字非常多,常用字就有6000多个,如果像ASCII编码表那样只使用1个字节最多只能表示256个汉字、所以我们使用2个字节来编码。
GB2312编码
我们首先定义的就是GB2312编码,它把 ASCII码表127之后的扩展字符集直接取消掉,并规定小于127的编码按原来的ASCII标准解释字符,当2个大于127的字符联结在一起时,就表示1个汉字。
第一个字节使用(0xA1-0xFE)编码,第2个字节使用(0xA1-0xFE)编码,这样的编码组合起来可以表示了7000多个符号,其中包括汉字6763个汉字。在这些编码里,我们还把数学符号、罗马字母、日文片假名等都编进表中,就连原来在ASCII表中原有的数字、标点以及字母也重新编了2个字节长的编码,这就是平时在输入法可以切换“全角”和“半角”符号的原因,半角就是原来的1个字节的ASCII编码。
下面的表格说明GB2312兼容ASCII码的原理,说明了GB2312是如何兼容ASCII的,当我们设定系统使用GB2312标准的时候,它遇到一个字符串时,会按字节检测值得大小,若遇到连续两个字节得数值都大于127时,就把这两个连续得字节合在一起,用GB2312解码,若遇到得数值小于127,就直接用ASCII解码。
第1字节 | 第2字节 | 表示的字符 | 说明 |
0x68 | 0x69 | (hi) | 两个字节的值都小于127(0x7F),使用ASCII解码 |
0xB0 | 0xA1 | (啊) | 两个字节的值都大于127(0x7F),使用GB2312解码 |
区位码
在GB2312编码的实际使用中,有时会用到区位码的概念,见图GB2312的部分区位码。GB2312编码对所收录字符进行了“分区”处理,共94个区,每区含有94个位,共8836个码位。而区位码实际是GB2312编码的内部形式,它规定对收录的每个字符采用两个字节表示,第一个字节为“高字节”,对应94个区;第二个字节为低字节,对应94个位。所以它的区位码范围就是:0x0101-0x9494。为兼容ASCII码,区号和位号分别加上0xA0偏移就得到GB2312编码。在区位码上加上0xA0,可求得GB2312编码的范围:0xA1A1-0XFEFE,其中汉字的编码范围是0xB0A1-0XF7FE,第一字节0xB0-0xF7(对应位号16-87),第二字节0xA1-0XFE(对应位号01-94)。
![](https://i-blog.csdnimg.cn/blog_migrate/b1d2f832b01eedf8c1e40efab3db7d8e.png)
GBK编码
第1字节 | 第2字节 | 第3字节 | 表示的字符 | 说明 |
0x68(<7F) | 0xB0(>7F) | 0xA1(>7F) | h啊 | 第1字节小于127,使用ASCII解码,第2字节大于127直接使用GBK解码,兼容GB2312 |
0xB0(>7F) | 0xA1(>7F) | 0X68(<7F) | 啊h | 第1字节大于127,直接使用GBK解码,第3字节小于127直接使用ASCII解码 |
0XB0(>7F) | 0X56(<7F) | 0X68(<7F) | 痴h | 第1字节大于127,第2字节虽然小于127,直接使用GBK解码,第3字节小于127直接使用ASCII解码 |
后面还有GB18030编码,使用4字节编码,Big5繁体中文编码,由于篇幅原因,可以有兴趣的网上了解。
Unicode字符集和编码
UTF-32
字符 | GBK编码 | Unicode编号 | UTF-32编码 |
A | 0x41 | 0x0000 0041 | 大端格式0x0000 0041 |
啊 | 0xB0A1 | 0x0000 554A | 大端格式0x0000 554A |
对UTF-32数据进行解码的时候,以4字节为单位进行解析即可,根据编码可直接找到Unicode字符集中对应编号的字符。
UTF-32的优点是编码简单,解码方便,读取编码的时候每次都直接读4字节,不需要加其他的判断。它的缺点是浪费存储空间,大量常用的字符的编号只需要两个字节就能表示。其次在存储的时候需要指定字节顺序,是高位字节存储在前(大端格式),还是低位字节存储在前(小端格式)。
UTF-16
针对UTF-32的缺点,人们改进了UTF-16的编码方式,如表格UTF-16编码示例,它采用2字节或4字节的变长编码方式(UTF-32为定长编码方式)。对Unicode字符编号在0-65535的统一使用2字节来表示,将每个字符的编号转换为2字节的二进制数,即从0x0000到0xFFFF.而由
字符 | GB18030编码 | Unicode编号 | UTF-16编码 |
A | 0x41 | 0X0000 0041 | 大端格式0x0041 |
啊 | 0xB0A1 | 0x0000 554A | 大端格式0x554A |
𧗌 | 0x9735 F832 | 0x0002 75CC | 大端格式0xD85D DDCC |
UTF-8
Unicode(16进制) | UTF-8(2进制) | ||||
编号范围 | 第1字节 | 第2字节 | 第3字节 | 第4字节 | 第5字节 |
00000000-0000007F | 0xxxxxxx | ||||
00000080-000007FF | 110xxxxx | 10xxxxxx | |||
00000800-0000FFFF | 1110xxxx | 10xxxxxx | 10xxxxxx | ||
00010000-0010FFFF | 11110xxx | 10xxxxxx | 10xxxxxx | 10xxxxxx | |
... | 111110xx | 10xxxxxx | 10xxxxxx | 10xxxxxx | 10xxxxxx |
字模
如果有字符编码、计算机还不知道如何表达该字符,因为字符实际上是一个个独特的图形,计算机必须把字符编码转化成对应的字符图形人类才能正常识别,因此我们要给计算机提供字符的图形数据,这些数据就是字模,多个字模数据组成的文件就是字库。
字模的构成
![](https://i-blog.csdnimg.cn/blog_migrate/55a425505c507bc4d34a8d7213b3342e.png)
字模显示原理
如何制作字模
- 配置字模格式
- 生成GB2312字模
字模寻址公式
存储字模文件
各种模式的液晶显示字符实验
显示ASCII编码的字符
编程要点
(1)获取字模数据
(2)根据字模格式,编写液晶显示函数
(3)编写测试程序,控制液晶
代码分析
ASCII字模数据
要显示的字符首先要有字库数据,在工程中fonts,c文件我们定义了一系列大小为24x32、16x24、16x16的ASCII码表的字模数据:如下
/*
*常用ASCII表,偏移量32,大小为8(宽度)*16(高度)
*/
const uint8_t ASCII8x16_Table[] = { //@consolas字体,阴码点阵格式,逐行顺向取摸
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x18,0x18,0x18,0x18,0x18,0x18,0x08,0x00,0x08,0x18,0x00,0x00,0x00,
0x00,0x00,0x00,0x34,0x24,0x24,0x24,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x16,0x24,0x7f,0x24,0x24,0x24,0x7e,0x24,0x24,0x00,0x00,0x00,
0x00,0x00,0x00,0x08,0x3e,0x68,0x48,0x68,0x1c,0x16,0x12,0x12,0x7c,0x10,0x10,0x00,
0x00,0x00,0x00,0x61,0xd2,0x96,0x74,0x08,0x10,0x16,0x29,0x49,0xc6,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x3c,0x64,0x64,0x38,0x72,0x4a,0xce,0x46,0x7f,0x00,0x00,0x00,
0x00,0x00,0x00,0x18,0x18,0x18,0x18,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x04,0x08,0x18,0x10,0x30,0x30,0x30,0x30,0x10,0x10,0x18,0x0c,0x04,
0x00,0x00,0x00,0x20,0x10,0x08,0x08,0x0c,0x04,0x04,0x04,0x0c,0x08,0x18,0x10,0x20,
0x00,0x00,0x00,0x08,0x0a,0x34,0x1c,0x6a,0x08,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x18,0x18,0x18,0x7f,0x18,0x18,0x18,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x18,0x18,0x08,0x30,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x3c,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x18,0x18,0x00,0x00,0x00,
0x00,0x00,0x00,0x02,0x06,0x04,0x0c,0x08,0x08,0x10,0x10,0x20,0x20,0x40,0x00,0x00,
0x00,0x00,0x00,0x00,0x3c,0x66,0x42,0x47,0x5b,0x73,0x42,0x66,0x3c,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x18,0x78,0x48,0x08,0x08,0x08,0x08,0x08,0x7e,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x3c,0x46,0x06,0x06,0x04,0x08,0x10,0x20,0x7e,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x7c,0x06,0x06,0x04,0x3c,0x02,0x02,0x06,0x7c,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x0c,0x1c,0x14,0x24,0x64,0x44,0xff,0x04,0x04,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x7e,0x60,0x60,0x60,0x7e,0x02,0x02,0x06,0x7c,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x1e,0x30,0x60,0x48,0x76,0x42,0x42,0x62,0x3c,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x7e,0x02,0x06,0x04,0x0c,0x08,0x18,0x10,0x30,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x3c,0x62,0x42,0x36,0x1c,0x66,0x42,0x42,0x3c,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x3c,0x66,0x42,0x42,0x66,0x1a,0x02,0x04,0x78,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x18,0x18,0x00,0x00,0x00,0x18,0x18,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x18,0x18,0x00,0x00,0x00,0x18,0x18,0x08,0x30,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x04,0x18,0x30,0x60,0x10,0x0c,0x06,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x7e,0x00,0x7e,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x30,0x18,0x04,0x06,0x0c,0x10,0x20,0x00,0x00,0x00,
0x00,0x00,0x00,0x30,0x1c,0x06,0x06,0x06,0x18,0x10,0x00,0x10,0x10,0x00,0x00,0x00,
0x00,0x00,0x00,0x1c,0x22,0x41,0x41,0xdd,0xb5,0xa5,0xa5,0xaf,0x94,0xc0,0x40,0x3c,
0x00,0x00,0x00,0x00,0x18,0x1c,0x34,0x24,0x26,0x62,0x7e,0x43,0xc1,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x7c,0x46,0x42,0x46,0x7c,0x42,0x42,0x42,0x7c,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x1e,0x20,0x40,0x40,0x40,0x40,0x40,0x60,0x3e,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x7c,0x46,0x42,0x43,0x43,0x43,0x42,0x46,0x78,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x7e,0x60,0x60,0x60,0x7e,0x60,0x60,0x60,0x7e,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x7e,0x60,0x60,0x60,0x7e,0x60,0x60,0x60,0x60,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x1e,0x60,0x40,0x40,0xce,0x42,0x42,0x62,0x3e,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x42,0x42,0x42,0x42,0x7e,0x42,0x42,0x42,0x42,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x7e,0x18,0x18,0x18,0x18,0x18,0x18,0x18,0x7e,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x7c,0x04,0x04,0x04,0x04,0x04,0x04,0x44,0x78,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x42,0x44,0x48,0x50,0x70,0x58,0x4c,0x44,0x42,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x3e,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x62,0x66,0x67,0x5f,0x5b,0x5b,0xc1,0xc1,0xc1,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x62,0x62,0x72,0x52,0x5a,0x4a,0x4e,0x46,0x46,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x3c,0x62,0x43,0xc3,0xc3,0xc3,0x43,0x62,0x3c,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x7c,0x46,0x42,0x42,0x46,0x78,0x40,0x40,0x40,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x3c,0x62,0x43,0xc3,0xc3,0xc3,0x43,0x62,0x3c,0x18,0x0f,0x00,
0x00,0x00,0x00,0x00,0x7c,0x66,0x62,0x66,0x7c,0x6c,0x64,0x66,0x62,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x3e,0x60,0x40,0x60,0x1c,0x06,0x02,0x02,0x7c,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x7f,0x18,0x18,0x18,0x18,0x18,0x18,0x18,0x18,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x42,0x42,0x42,0x42,0x42,0x42,0x42,0x62,0x3c,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0xc1,0x43,0x42,0x62,0x26,0x24,0x34,0x1c,0x18,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0xc1,0xc1,0x41,0x49,0x5b,0x5b,0x76,0x66,0x66,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x43,0x66,0x34,0x18,0x18,0x1c,0x24,0x66,0xc3,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0xc1,0x42,0x66,0x34,0x1c,0x18,0x18,0x18,0x18,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x7e,0x02,0x04,0x0c,0x18,0x10,0x20,0x60,0x7e,0x00,0x00,0x00,
0x00,0x00,0x00,0x1c,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x1c,
0x00,0x00,0x00,0x40,0x20,0x20,0x10,0x10,0x08,0x08,0x0c,0x04,0x06,0x02,0x00,0x00,
0x00,0x00,0x00,0x3c,0x0c,0x0c,0x0c,0x0c,0x0c,0x0c,0x0c,0x0c,0x0c,0x0c,0x0c,0x3c,
0x00,0x00,0x00,0x00,0x18,0x1c,0x24,0x62,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xff,
0x00,0x00,0x00,0x20,0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x3c,0x06,0x02,0x3e,0x42,0x46,0x7a,0x00,0x00,0x00,
0x00,0x00,0x00,0x40,0x40,0x40,0x5c,0x62,0x42,0x42,0x42,0x42,0x7c,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x1e,0x20,0x60,0x40,0x60,0x20,0x3e,0x00,0x00,0x00,
0x00,0x00,0x00,0x02,0x02,0x02,0x3e,0x62,0x42,0x42,0x42,0x66,0x3a,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x3c,0x62,0x42,0x7e,0x40,0x60,0x3e,0x00,0x00,0x00,
0x00,0x00,0x00,0x0f,0x18,0x10,0x10,0x7e,0x10,0x10,0x10,0x10,0x10,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x3f,0x66,0x42,0x66,0x58,0x40,0x3e,0x43,0x42,0x3c,
0x00,0x00,0x00,0x40,0x40,0x40,0x5c,0x62,0x42,0x42,0x42,0x42,0x42,0x00,0x00,0x00,
0x00,0x00,0x00,0x18,0x18,0x00,0x78,0x08,0x08,0x08,0x08,0x08,0x7e,0x00,0x00,0x00,
0x00,0x00,0x00,0x04,0x0c,0x00,0x7c,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x0c,0x78,
0x00,0x00,0x00,0x60,0x60,0x60,0x62,0x6c,0x78,0x70,0x68,0x64,0x62,0x00,0x00,0x00,
0x00,0x00,0x00,0x78,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x7e,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x76,0x4b,0x4b,0x4b,0x4b,0x4b,0x4b,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x5c,0x62,0x42,0x42,0x42,0x42,0x42,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x3c,0x62,0x42,0x43,0x42,0x62,0x3c,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x5c,0x62,0x42,0x42,0x42,0x42,0x7c,0x40,0x40,0x40,
0x00,0x00,0x00,0x00,0x00,0x00,0x3e,0x62,0x42,0x42,0x42,0x66,0x3a,0x02,0x02,0x02,
0x00,0x00,0x00,0x00,0x00,0x00,0x6e,0x72,0x63,0x60,0x60,0x60,0x60,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x3e,0x20,0x20,0x3c,0x06,0x02,0x7c,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x10,0x10,0xfe,0x10,0x10,0x10,0x10,0x10,0x1e,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x42,0x42,0x42,0x42,0x42,0x66,0x3a,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x43,0x42,0x66,0x24,0x34,0x18,0x18,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0xc1,0xc1,0x5b,0x5a,0x5e,0x66,0x66,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x62,0x26,0x1c,0x18,0x1c,0x26,0x62,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x43,0x42,0x66,0x24,0x34,0x1c,0x18,0x18,0x30,0xe0,
0x00,0x00,0x00,0x00,0x00,0x00,0x7e,0x06,0x0c,0x18,0x10,0x20,0x7e,0x00,0x00,0x00,
0x00,0x00,0x00,0x0e,0x18,0x10,0x10,0x10,0x30,0x70,0x10,0x10,0x10,0x10,0x18,0x0e,
0x00,0x00,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,
0x00,0x00,0x00,0x30,0x18,0x08,0x08,0x08,0x0c,0x0e,0x08,0x08,0x08,0x08,0x18,0x30,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x71,0x4b,0x06,0x00,0x00,0x00,0x00,0x00,
};
管理英文字模的结构体
为了方便使用各种不同的字体,工程中定义了一个sFONT的结构体类型,并利用它定义了存储不同字体信息的结构体变量。
typedef struct _tFont
{
const uint8_t *table;
uint16_t Width;
uint16_t Height;
}sFONT;
sFONT ASCII_8x16 = {
ASCII8x16_Table,
8,
16,
};
sFONT ASCII_16x16 = {
ASCII16x24_Table,
16,
24,
};
sFONT ASCII_24x32 = {
ASCII24x32_Table,
24,
32,
};
ASCII字符和中文显示函数
/**************************以下是ASCII英文字符显示相关的函数**********************************/
/*
*@brief 显示字符
*@param usX:在特定扫描方向字符显示的X起始位置
usY:在特定扫描方向字符显示的Y起始位置
Chara:要显示的字符数据
*@revtal:None
*/
void ILI9341_LCD_DisChar_EN(uint16_t usX,uint16_t usY,const char Chara)
{
uint8_t byteCount,bitCount,fontLength;
uint16_t usRelativePosition;
uint8_t *Pfont;
/*对ASCII表的偏移(注意:字模表不包含ASCII表的前32个非图形符号)*/
usRelativePosition = Chara - ' ';
/*一个字符的字模数据所占的字节数*/
fontLength = ((*LCD_Currentfonts).Width*(*LCD_Currentfonts).Height)/8;
/*字模的首地址,ASCII表偏移乘以每个字模的字节数,求出字模的偏移位置*/
Pfont = (uint8_t *)&LCD_Currentfonts->table[usRelativePosition*fontLength];
/*设置显示窗口*/
ILI9341_Open_Window(usX,usY,LCD_Currentfonts->Width,LCD_Currentfonts->Height);
/*按字节读取字模数据显示*/
ILI9341_Write_Cmd(CMD_SetPixel);
/*由于前面设置了显示窗口,显示数据会自动换行*/
for(byteCount=0;byteCount<fontLength;byteCount++)
{ /*一位一位处理要显示的颜色*/
for(bitCount=0;bitCount<8;bitCount++)
{
if((*Pfont)&(0x80>>bitCount))
{
ILI9341_Write_Data(CurrentTextColor);
}
else
{
ILI9341_Write_Data(CurrentBackColor);
}
}
Pfont++;
}
}
/*
*@brief 显示一串英文字符串
*@param usX:要显示的英文字符串的起始X位置
usY:要显示的英文字符串的起始Y位置
Str:要显示的英文字符串
*@retval:None
*/
void ILI9341_LCD_DisStr_EN(uint16_t usX,uint16_t usY, char *Str)
{
/*先要根据字符串的字符找到对应的字模数据*/
while(*Str != '\0')
{
if((usX + LCD_Currentfonts->Width)>LCD_X_LENGTH)
{
usX = ILI9341_DispWindow_X_Star;
usY += LCD_Currentfonts->Height ;
}
if((usY + LCD_Currentfonts->Height)>LCD_Y_LENGTH)
{
usX = ILI9341_DispWindow_X_Star;
usY = ILI9341_DispWindow_Y_Star;
}
ILI9341_LCD_DisChar_EN(usX,usY,*Str);
Str++;
usX += LCD_Currentfonts->Width;
}
}
/*
*@brief 在显示屏上显示英文字符(沿着Y轴方向,前面默认是沿着X轴方向)
*@param usX:在特定的扫描方向上要显示英文字符串的X位置
usY:在特定的扫描方向下要显示英文字符串的Y位置
*@retval:None
*/
void ILI9341_LCD_DisStr_EN_Ydir(uint16_t usX,uint16_t usY,char *Str)
{
while(*Str != '\0')
{
if((usY + LCD_Currentfonts->Height)>LCD_Y_LENGTH)
{
usX += LCD_Currentfonts->Width;
usY = ILI9341_DispWindow_Y_Star;
}
if((usX + LCD_Currentfonts->Width)>LCD_X_LENGTH)
{
usX = ILI9341_DispWindow_X_Star;
usY = ILI9341_DispWindow_Y_Star;
}
ILI9341_LCD_DisChar_EN(usX,usY,*Str);
Str++;
usY += LCD_Currentfonts->Height;
}
}
/*
*@brief 在ILI9341显示器上显示英文字符串
*@param line:在特定扫描方向上英文字符串的起始Y坐标
*@note:本参数可以使用宏定义LINE(0)、LINE(1)等指定方式的文字坐标
其中宏LINE会根据选择的当前字体来计算Y坐标值
Str:要显示的英文字符串的首地址
*@retval:None
*/
void ILI9341_LCD_DisStrLine_EN(uint16_t line,char *Str)
{
uint16_t usX = 0;
while(*Str != '\0')
{
if((usX + LCD_Currentfonts->Width)>LCD_X_LENGTH)
{
usX = ILI9341_DispWindow_X_Star;
line += LCD_Currentfonts->Height;
}
if((line + LCD_Currentfonts->Height)>LCD_Y_LENGTH)
{
usX = ILI9341_DispWindow_X_Star;
line = ILI9341_DispWindow_Y_Star;
}
ILI9341_LCD_DisChar_EN(usX,line,*Str);
Str++;
usX += LCD_Currentfonts->Width;
}
}
/*
*@brief 设置当前要显示的字体大小
*@param fonts:指定要选择的字体
*@note:参数可以为以下选择之一:
*@arg:ASCII_8x16
*@arg:ASCII_8x16
*@arg:ASCII_8x16
*@retval:None
*/
void LCD_SetFont(sFONT *fonts)
{
LCD_Currentfonts = fonts;
}
/*
*brief 读取当前字体的类型
*param None
*retval:返回当前字体的类型
*/
sFONT *LCD_GetFont(void)
{
return LCD_Currentfonts;
}
/**************************以下是有关GB2312中文字符显示相关的函数********************************************/
/*
*@brief 显示GB2312中文字符
*@param usX:在当前扫描方式下的要显示的中文字符的X起始位置
usY:在当前扫描方式下的要显示的中文字符的Y起始位置
*@retval:None
*/
void ILI9341_LCD_DisChar_CH ( uint16_t usX, uint16_t usY, uint16_t usChar )
{
uint8_t rowCount, bitCount;
uint8_t ucBuffer [ CH_WIDTH*CH_HEIGHT/8 ];
uint16_t usTemp;
//设置显示窗口
ILI9341_Open_Window ( usX, usY, CH_WIDTH, CH_HEIGHT );
ILI9341_Write_Cmd ( CMD_SetPixel );
//取字模数据
GetGBKCode ( ucBuffer, usChar );
for ( rowCount = 0; rowCount < CH_HEIGHT; rowCount++ )
{
/* 取出两个字节的数据,在lcd上即是一个汉字的一行 */
usTemp = ucBuffer [ rowCount * 2 ];
usTemp = ( usTemp << 8 );
usTemp |= ucBuffer [ rowCount * 2 + 1 ];
for ( bitCount = 0; bitCount < CH_WIDTH; bitCount ++ )
{
if ( usTemp & ( 0x8000 >> bitCount ) ) //高位在前
ILI9341_Write_Data ( CurrentTextColor );
else
ILI9341_Write_Data ( CurrentBackColor );
}
}
}
/*
*@brief 在ILI9341显示器上显示中文字符串
*@param usX:在当前扫描方式下的显示中文字符串的X起始位置
usY:在当前扫描方式下的显示中文字符串的Y起始位置
*@retval:None
*/
void ILI9341_LCD_DisStr_CH(uint16_t usX,uint16_t usY,char *uStr)
{
uint16_t usCh;
while(*uStr!='\0')
{
if((usX + CH_WIDTH)>LCD_X_LENGTH)
{
usX = ILI9341_DispWindow_X_Star;
usY += CH_HEIGHT;
}
if((usY + CH_HEIGHT)>LCD_Y_LENGTH)
{
usX = ILI9341_DispWindow_X_Star;
usY = ILI9341_DispWindow_Y_Star;
}
usCh = *(uint16_t *)uStr;
usCh = (usCh<<8) + (usCh>>8);
ILI9341_LCD_DisChar_CH(usX,usY,usCh);
uStr+=2;
usX += CH_WIDTH;
}
}
/**
* @brief 在 ILI9341 显示器上显示中英文字符串
* @param usX :在特定扫描方向下字符的起始X坐标
* @param usY :在特定扫描方向下字符的起始Y坐标
* @param pStr :要显示的字符串的首地址
* @note 可使用LCD_SetBackColor、LCD_SetTextColor、LCD_SetColors函数设置颜色
* @retval 无
*/
void ILI9341_DispString_EN_CH ( uint16_t usX , uint16_t usY, char * pStr )
{
uint16_t usCh;
while( * pStr != '\0' )
{
if ( * pStr < 127 ) //英文字符
{
if ( ( usX - ILI9341_DispWindow_X_Star + LCD_Currentfonts->Width ) > LCD_X_LENGTH )
{
usX = ILI9341_DispWindow_X_Star;
usY += LCD_Currentfonts->Height;
}
if ( ( usY - ILI9341_DispWindow_Y_Star + LCD_Currentfonts->Height ) > LCD_Y_LENGTH )
{
usX = ILI9341_DispWindow_X_Star;
usY = ILI9341_DispWindow_Y_Star;
}
ILI9341_LCD_DisChar_EN ( usX, usY, * pStr );
usX += LCD_Currentfonts->Width;
pStr ++;
}
else //汉字字符
{
if ( ( usX - ILI9341_DispWindow_X_Star + CH_WIDTH ) > LCD_X_LENGTH )
{
usX = ILI9341_DispWindow_X_Star;
usY += CH_HEIGHT;
}
if ( ( usY - ILI9341_DispWindow_Y_Star + CH_HEIGHT ) > LCD_Y_LENGTH )
{
usX = ILI9341_DispWindow_X_Star;
usY = ILI9341_DispWindow_Y_Star;
}
usCh = * ( uint16_t * ) pStr;
usCh = ( usCh << 8 ) + ( usCh >> 8 );
ILI9341_LCD_DisChar_CH ( usX, usY, usCh );
usX += CH_WIDTH;
pStr += 2; //一个汉字两个字节
}
}
}
/*
*@brief
*@param
*@retval
*/
void ILI9341_LCD_DisStr_CH_EN_Line(uint16_t line,char *pStr)
{
uint16_t usCh;
uint16_t usX=0;
while(*pStr!='\0')
{
if(*pStr<127)
{
if((usX+LCD_Currentfonts->Width)>LCD_X_LENGTH)
{
usX = ILI9341_DispWindow_X_Star;
line += LCD_Currentfonts->Height;
}
if((line+LCD_Currentfonts->Height)>LCD_Y_LENGTH)
{
usX = ILI9341_DispWindow_X_Star;
line = ILI9341_DispWindow_Y_Star;
}
ILI9341_LCD_DisChar_EN(usX,line,*pStr);
usX += LCD_Currentfonts->Width;
pStr++;
}
else
{
if((usX+CH_WIDTH)>LCD_X_LENGTH)
{
usX = ILI9341_DispWindow_X_Star;
line += CH_HEIGHT;
}
if((line+CH_HEIGHT)>LCD_Y_LENGTH)
{
usX = ILI9341_DispWindow_X_Star;
line = ILI9341_DispWindow_Y_Star;
}
usCh = *(uint16_t *)pStr;
usCh = (usCh<<8) + (usCh>>8);
ILI9341_LCD_DisChar_CH(usX,line,usCh);
usX += CH_WIDTH;
pStr += 2;
}
}
}
/**
* @brief 在 ILI9341 显示器上显示中英文字符串(沿Y轴方向)
* @param usX :在特定扫描方向下字符的起始X坐标
* @param usY :在特定扫描方向下字符的起始Y坐标
* @param pStr :要显示的中英文字符串的首地址
* @note 可使用LCD_SetBackColor、LCD_SetTextColor、LCD_SetColors函数设置颜色
* @retval 无
*/
void ILI9341_DispString_EN_CH_YDir ( uint16_t usX,uint16_t usY , char * pStr )
{
uint16_t usCh;
while( * pStr != '\0' )
{
//统一使用汉字的宽高来计算换行
if ( ( usY - ILI9341_DispWindow_Y_Star + CH_HEIGHT ) >LCD_Y_LENGTH )
{
usY = ILI9341_DispWindow_Y_Star;
usX += CH_WIDTH;
}
if ( ( usX - ILI9341_DispWindow_X_Star + CH_WIDTH ) > LCD_X_LENGTH)
{
usX = ILI9341_DispWindow_X_Star;
usY = ILI9341_DispWindow_Y_Star;
}
//显示
if ( * pStr <= 126 ) //英文字符
{
ILI9341_LCD_DisChar_EN ( usX, usY, * pStr);
pStr ++;
usY += CH_HEIGHT;
}
else //汉字字符
{
usCh = * ( uint16_t * ) pStr;
usCh = ( usCh << 8 ) + ( usCh >> 8 );
ILI9341_LCD_DisChar_CH ( usX,usY , usCh );
usY += CH_HEIGHT;
pStr += 2; //一个汉字两个字节
}
}
}
/**
* @brief 清除某行文字
* @param Line: 指定要删除的行
* 本参数可使用宏LINE(0)、LINE(1)等方式指定要删除的行,
* 宏LINE(x)会根据当前选择的字体来计算Y坐标值,并删除当前字体高度的第x行。
* @retval None
*/
void LCD_ClearLine(uint16_t Line)
{
ILI9341_Clear(0,Line,LCD_X_LENGTH,((sFONT *)LCD_GetFont())->Height); /* 清屏,显示全黑 */
}
/*********************end of file*************************/