本帖最后由 jinglixixi 于 2023-6-24 11:17 编辑
#申请原创# @21小跑堂
LKS32MC071开发板是凌鸥创芯推出的一款面向电机控制的开发板,它采用的是一种组合结构,上层是核心板,底层则是面向电机控制的驱动板。 那么除了进行电机控制,该开发板还能用于哪方面呢? 本人是将它用在点阵板的显示驱动上,所驱动的是一款红色的P4.75点阵板,其显示规格为16*64点阵,它的外观如图1所示。 图1 点阵板外观
该点阵板采用的接口方式为HUB08,其引脚名称与排列方式如图2所示。 图2 HUB08接口
该点阵板与开发板的连接关系为: A ---P0.0 B ---P0.4 C ---P1.10 D ---P1.11 R1 ---P0.14 OE ---P2.2 LAT ---P2.3 CLK ---P2.7
所用引脚输出高低电平的语句定义为: #defineLR1_high GPIO_SetBits(GPIO0,GPIO_Pin_14) #defineLR1_low GPIO_ResetBits(GPIO0,GPIO_Pin_14) #defineCLK_high GPIO_SetBits(GPIO2,GPIO_Pin_7) #defineCLK_low GPIO_ResetBits(GPIO2,GPIO_Pin_7) #defineLA_high GPIO_SetBits(GPIO0,GPIO_Pin_0) #defineLA_low GPIO_ResetBits(GPIO0,GPIO_Pin_0) #defineLB_high GPIO_SetBits(GPIO0,GPIO_Pin_4) #defineLB_low GPIO_ResetBits(GPIO0, GPIO_Pin_4) #defineLC_high GPIO_SetBits(GPIO1,GPIO_Pin_10) #defineLC_low GPIO_ResetBits(GPIO1,GPIO_Pin_10) #defineLD_high GPIO_SetBits(GPIO1,GPIO_Pin_11) #defineLD_low GPIO_ResetBits(GPIO1,GPIO_Pin_11) #defineLEN_high GPIO_SetBits(GPIO2,GPIO_Pin_2) #defineLEN_low GPIO_ResetBits(GPIO2,GPIO_Pin_2) #defineLSTB_high GPIO_SetBits(GPIO2,GPIO_Pin_3)
- void dzb_init(void)
- {
- GPIO_InitTypeDef GPIO_InitStruct;
- GPIO_StructInit(&GPIO_InitStruct);
- GPIO_StructInit(&GPIO_InitStruct);
- GPIO_InitStruct.GPIO_Mode = GPIO_Mode_OUT;
- GPIO_InitStruct.GPIO_Pin = GPIO_Pin_0|GPIO_Pin_4|GPIO_Pin_14;
- GPIO_Init(GPIO0, &GPIO_InitStruct);
- GPIO_StructInit(&GPIO_InitStruct);
- GPIO_InitStruct.GPIO_Mode = GPIO_Mode_OUT;
- GPIO_InitStruct.GPIO_Pin = GPIO_Pin_10|GPIO_Pin_11;
- GPIO_Init(GPIO1, &GPIO_InitStruct);
- GPIO_StructInit(&GPIO_InitStruct);
- GPIO_InitStruct.GPIO_Mode = GPIO_Mode_OUT;
- GPIO_InitStruct.GPIO_Pin = GPIO_Pin_2|GPIO_Pin_3|GPIO_Pin_7;
- GPIO_Init(GPIO2, &GPIO_InitStruct);
- }
为了向点阵板发送16位的显示数据,所配置的函数为: - void OutByte(uint16_t dat)
- {
- uint8_t i=0 ;
- for(i=0;i<16;i++)
- {
- CLK_low;
- if(dat&0x8000)
- {
- LR1_high;
- }
- else
- {
- LR1_low;
- }
- dat=dat<<1;
- CLK_high;
- }
- }
相应的行地址输出函数为: - void SeleRow(uint8_t Nd)
- {
- uint8_t N;
- N=Nd;
- N=N%16;
- if(N&0x01) LA_high;
- else LA_low;
- if (N&0x02) LB_high;
- else LB_low;
- if (N&0x04) LC_high;
- else LC_low;
- if (N&0x08) LD_high;
- else LD_low;
- }
实现多列数据发送的函数为: - voidDisCol(uint16_t dat,uint16_t len)
- {
- while(len--)
- {
- OutByte(dat);
- }
- }
进行驱动测试的函数为: - void Display(void)
- {
- DisCol(0x5555,4);
- LEN_high;
- LSTB_high;
- LSTB_low;
- SeleRow(ScanRow);
- LEN_low;
- ScanRow++;
- if(ScanRow>15) ScanRow=0;
- }
对应的主程序为: - int main(void)
- {
- Hardware_init();
- ScanRow=0;
- dzb_init();
- for (;;)
- {
- Display();
- }
- }
经程序的编译和下载,其显示效果如图3所示,说明情况正常。
图3测试效果
以此为基础,在添加字库的情况下,则可进行汉字的显示。 其配置的字库结构为: uint8_tV[]={ // 远上寒山石径斜白云生处有人家 … 0x00,0x00,0xF8,0x23,0x00,0x10,0x00,0x10,0x00,0x00,0xFC,0x07,0x20,0xF1,0x20,0x11, 0x20,0x11,0x20,0x11,0x24,0x11,0x24,0x12,0x24,0x12,0x1C,0x14,0x00,0x28,0xFE,0x47,/*0*/ 0x00,0x02,0x00,0x02,0x00,0x02,0x00,0x02,0x00,0x02,0x00,0x02,0xF8,0x03,0x00,0x02, 0x00,0x02,0x00,0x02,0x00,0x02,0x00,0x02,0x00,0x02,0x00,0x02,0xFE,0xFF,0x00,0x00,/*1*/ 0x00,0x02,0x00,0x01,0xFE,0x7F,0x42,0x44,0xF4,0x9F,0x40,0x04,0xF8,0x3F,0x40,0x04, 0xFE,0xFF,0x20,0x08,0x10,0x13,0x88,0x20,0x46,0xC0,0x00,0x06,0x80,0x01,0x40,0x00,/*2*/ 0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x08,0x21,0x08,0x21,0x08,0x21,0x08,0x21, 0x08,0x21,0x08,0x21,0x08,0x21,0x08,0x21,0x08,0x21,0xF8,0x3F,0x08,0x00,0x00,0x00,/*3*/ ... };
为配合字库的显示,需对函数DisCol() 和Display()加以调整。 修改后的DisCol()函数为: - voidDisCol(uint16_t lenght)
- {
- uint16_tdat;
- uint8_t m=0; // 远上寒山石径斜 白云深处有人家
- while(lenght--)
- {
- dat=(V[m*32+ScanRow*2+1]<<8)+V[m*32+ScanRow*2];
- OutByte(dat);
- m=m+1;
- }
- }
修改后的Display()函数为:
- void Display(void)
- {
- DisCol(4);
- LEN_high;
- LSTB_high;
- LSTB_low;
- SeleRow(ScanRow);
- LEN_low;
- ScanRow++;
- if(ScanRow>15) ScanRow=0;
- }
重新编译和下载后,其显示效果见图4所示。
图4中文显示效果 除了文字信息的显示,数据也是显示的主要内容,为此还需为其配置一个字符库,其存储结构为: uint8_tS[]={ 0x00,0x00,0x00,0x18,0x24,0x42,0x42,0x42,0x42,0x42,0x42,0x42,0x24,0x18,0x00,0x00,/*"0",0*/ 0x00,0x00,0x00,0x08,0x0E,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x08,0x3E,0x00,0x00,/*"1",1*/ 0x00,0x00,0x00,0x3C,0x42,0x42,0x42,0x20,0x20,0x10,0x08,0x04,0x42,0x7E,0x00,0x00,/*"2",2*/ 0x00,0x00,0x00,0x3C,0x42,0x42,0x20,0x18,0x20,0x40,0x40,0x42,0x22,0x1C,0x00,0x00,/*"3",3*/ 0x00,0x00,0x00,0x20,0x30,0x28,0x24,0x24,0x22,0x22,0x7E,0x20,0x20,0x78,0x00,0x00,/*"4",4*/ 0x00,0x00,0x00,0x7E,0x02,0x02,0x02,0x1A,0x26,0x40,0x40,0x42,0x22,0x1C,0x00,0x00,/*"5",5*/ 0x00,0x00,0x00,0x38,0x24,0x02,0x02,0x1A,0x26,0x42,0x42,0x42,0x24,0x18,0x00,0x00,/*"6",6*/ 0x00,0x00,0x00,0x7E,0x22,0x22,0x10,0x10,0x08,0x08,0x08,0x08,0x08,0x08,0x00,0x00,/*"7",7*/ 0x00,0x00,0x00,0x3C,0x42,0x42,0x42,0x24,0x18,0x24,0x42,0x42,0x42,0x3C,0x00,0x00,/*"8",8*/ 0x00,0x00,0x00,0x18,0x24,0x42,0x42,0x42,0x64,0x58,0x40,0x40,0x24,0x1C,0x00,0x00,/*"9",9*/ 0x00,0x00,0x00,0x00,0x00,0x00,0x18,0x18,0x00,0x00,0x00,0x00,0x18,0x18,0x00,0x00,/*":",10*/ 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFE,0x00,0x00,0x00,0x00,0x00,0x00,0x00,/*"-",11*/ 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, /*" ",12*/ };
因取模方式的不同,需对OutByte()函数加以调整,其修改后的内容为: - voidOut Byte (u16 dat)
- {
- u8 i=0 ;
- for(i=0;i<16;i++)
- {
- CLK_low;
- if(dat&0x0001)
- {
- LR1_high;
- }
- else
- {
- LR1_low;
- }
- dat=dat>>1;
- CLK_high;
- }
- }
所对应的DisCol()函数则修改为: - voidDisCol(u16 lenght)
- {
- u16dat;
- u8 m=0;
- u8 sj[]={0x01,0x02,0x0A,0x03,0x00,0x0A,0x03,0x00}; // 存放显示内容 0~9:- 等
- while(lenght--)
- {
- dat=(S[sj[m+1]*16+ScanRow]<<8)+S[sj[m]*16+ScanRow];
- OutByte(dat);
- m=m+2;
- }
- }
所实现的数据所示效果见图5所示,当然要让时钟真的行走起来还需RTC的配合。因片内没有配置RTC计时器,以此要使用RTC计时功能需外挂DS1302这样的功能模块。 图5数值显示效果
|