zoukankan      html  css  js  c++  java
  • 学习2__STM32--汉字显示

     汉字显示操作流程

    第一,进入主函数

     1  int main(void)
     2  {     
     3     u32 fontcnt;          
     4     u8 i,j;
     5     u8 fontx[2];//gbk码
     6     u8 key,t;              
     7  
     8     delay_init();            //延时函数初始化      
     9     NVIC_Configuration();    //设置NVIC中断分组2:2位抢占优先级,2位响应优先级
    10     uart_init(9600);         //串口初始化为9600
    11     LED_Init();              //LED端口初始化
    12     LCD_Init();              //初始化液晶 
    13     KEY_Init();              //按键初始化
    14     usmart_dev.init(72); //usmart初始化    
    15     mem_init(SRAMIN);    //初始化内部内存池    
    16 
    17     exfuns_init();                    //为fatfs相关变量申请内存  
    18     f_mount(0,fs[0]);                 //挂载SD卡 
    19     f_mount(1,fs[1]);                 //挂载FLASH.
    20     key=KEY_Scan(0);                  //按键扫描
    21     LCD_ShowString(60,50,200,16,16,"Warship STM32");
    22  
    23     while(font_init()||key==KEY_UP) //检查字库
    24     {
    25 UPD:    
    26         LCD_Clear(WHITE);           //清屏
    27         POINT_COLOR=RED;            //设置字体为红色                    
    28         LCD_ShowString(60,50,200,16,16,"Warship STM32");
    29         while(SD_Initialize())        //检测SD卡
    30         {
    31             LCD_ShowString(60,70,200,16,16,"SD Card Failed!");
    32             delay_ms(200);
    33             LCD_Fill(60,70,200+60,70+16,WHITE);
    34             delay_ms(200);            
    35         }                                                             
    36         LCD_ShowString(60,70,200,16,16,"SD Card OK");
    37         LCD_ShowString(60,90,200,16,16,"Font Updating...");
    38         key=update_font(20,110,16,0);//从SD卡更新
    39         while(key)//更新失败        
    40         {                       
    41             LCD_ShowString(60,110,200,16,16,"Font Update Failed!");
    42             delay_ms(200);
    43             LCD_Fill(20,110,200+20,110+16,WHITE);
    44             delay_ms(200);               
    45         }           
    46         LCD_ShowString(60,110,200,16,16,"Font Update Success!");
    47         delay_ms(1500);    
    48         LCD_Clear(WHITE);//清屏           
    49     }

     主函数主要是做了,外设初始化,磁盘挂载,字库检查,显示汉字信息

    第二,进入检查字库函数

    1 u8 font_init(void)
    2 {                                                               
    3     SPI_Flash_Init();
    4     FONTINFOADDR=(1024*6+500)*1024;         //W25Q64,6M以后     
    5     ftinfo.ugbkaddr=FONTINFOADDR+25;        //UNICODEGBK 表存放首地址固定地址
    6     SPI_Flash_Read((u8*)&ftinfo,FONTINFOADDR,sizeof(ftinfo));//读出ftinfo结构体数据
    7     if(ftinfo.fontok!=0XAA)return 1;        //字库错误. 
    8     return 0;            
    9 }

    没有检测到字库就需要更新字库

    第3行,初始化Flash

    第4行,确定字库开始的地址,Flash的前6M给FatFS使用,后接500K用户使用区,

    第5行,再接25Bytes的字库表头信息

    第6行,读取表头结构体信息数据

    第7行,检测字库表头结构体成员字体正确标志

    第三,进入更新字库函数

     1 u8 update_font(u16 x,u16 y,u8 size,u8 src)
     2 {    
     3     u8 *gbk16_path;
     4     u8 *gbk12_path;
     5     u8 *unigbk_path;
     6     u8 res;          
     7     if(src)//从25qxx更新
     8     {
     9         unigbk_path=(u8*)UNIGBK_25QPATH;
    10         gbk12_path=(u8*)GBK12_25QPATH;
    11         gbk16_path=(u8*)GBK16_25QPATH;
    12     }else//从sd卡更新
    13     {
    14         unigbk_path=(u8*)UNIGBK_SDPATH;
    15         gbk12_path=(u8*)GBK12_SDPATH;
    16         gbk16_path=(u8*)GBK16_SDPATH;
    17     }   
    18     res=0XFF;        
    19     ftinfo.fontok=0XFF;
    20     SPI_Flash_Write((u8*)&ftinfo,FONTINFOADDR,sizeof(ftinfo));    //清除之前字库成功的标志.防止更新到一半重启,导致的字库部分数据丢失.
    21     SPI_Flash_Read((u8*)&ftinfo,FONTINFOADDR,sizeof(ftinfo));     //重新读出ftinfo结构体数据
    22     LCD_ShowString(x,y,240,320,size,"Updating UNIGBK.BIN");        
    23     res=updata_fontx(x+20*size/2,y,size,unigbk_path,0);           //更新UNIGBK.BIN
    24     if(res)return 1;
    25     LCD_ShowString(x,y,240,320,size,"Updating GBK12.BIN  ");
    26     res=updata_fontx(x+20*size/2,y,size,gbk12_path,1);            //更新GBK12.FON
    27     if(res)return 2;
    28     LCD_ShowString(x,y,240,320,size,"Updating GBK16.BIN  ");
    29     res=updata_fontx(x+20*size/2,y,size,gbk16_path,2);            //更新GBK16.FON
    30     if(res)return 3;       
    31     //全部更新好了
    32     ftinfo.fontok=0XAA;
    33     SPI_Flash_Write((u8*)&ftinfo,FONTINFOADDR,sizeof(ftinfo));    //保存字库信息
    34     return 0;//无错误.         
    35 }

    第7行,选择字库更新来源

    第8行,读取字库所在目录

    第19行,清除字库表头信息中的字库正确标志

    第20行,将修改过的字库表头信息写入Flash(修改了字库正常标志)

    第21行,将字库表头信息从Flash中读出,用以跟最后字库更新成功后的正常标志一起写入Flash

    第23行,更新字库文件

    第32行,在确认字库更新正确后,标志字库表头信息中的字库更新正常标志

    第33行,将最终正确的字库表头写入Flash,供之后检查字库使用

    字库更新底层函数

     1 u8 updata_fontx(u16 x,u16 y,u8 size,u8 *fxpath,u8 fx)
     2 {
     3     u32 flashaddr=0;                                    
     4     FIL * fftemp;
     5     u8 *tempbuf;
     6     u8 res;    
     7     u16 bread;
     8     u32 offx=0;
     9     u8 rval=0;         
    10     fftemp=(FIL*)mymalloc(SRAMIN,sizeof(FIL));    //分配内存    
    11     if(fftemp==NULL)rval=1;
    12     tempbuf=mymalloc(SRAMIN,4096);    //分配4096个字节空间
    13     if(tempbuf==NULL)rval=1;
    14     res=f_open(fftemp,(const TCHAR*)fxpath,FA_READ); 
    15     if(res)rval=2;      //打开文件失败  
    16     if(rval==0)     
    17     {
    18         if(fx==0)        //更新UNIGBK.BIN
    19         {
    20             ftinfo.ugbkaddr=FONTINFOADDR+sizeof(ftinfo);    //信息头之后,紧跟UNIGBK转换码表
    21             ftinfo.ugbksize=fftemp->fsize;                //UNIGBK大小
    22             flashaddr=ftinfo.ugbkaddr;
    23         }else if(fx==1)    //GBK12
    24         {                  
    25             ftinfo.f12addr=ftinfo.ugbkaddr+ftinfo.ugbksize;      //UNIGBK之后,紧跟GBK12字库
    26             ftinfo.gbk12size=fftemp->fsize;                      //GBK12字库大小
    27             flashaddr=ftinfo.f12addr;                            //GBK12的起始地址
    28         }else            //GBK16
    29         {
    30             ftinfo.f16addr=ftinfo.f12addr+ftinfo.gbk12size;      //GBK12之后,紧跟GBK16字库
    31             ftinfo.gkb16size=fftemp->fsize;                      //GBK16字库大小
    32             flashaddr=ftinfo.f16addr;                            //GBK16的起始地址
    33         }       
    34         while(res==FR_OK)//死循环执行
    35         {
    36             res=f_read(fftemp,tempbuf,4096,(UINT *)&bread);     //读取数据     
    37             if(res!=FR_OK)break;                                 //执行错误
    38             SPI_Flash_Write(tempbuf,offx+flashaddr,4096);        //从0开始写入4096个数据  
    39             offx+=bread;      
    40             fupd_prog(x,y,size,fftemp->fsize,offx);              //进度显示
    41             if(bread!=4096)break;                                //读完了.
    42         }     
    43         f_close(fftemp);        
    44     }             
    45     myfree(SRAMIN,fftemp);    //释放内存
    46     myfree(SRAMIN,tempbuf);    //释放内存
    47     return res;
    48 }

    第14行,打开字库文件,获取fftemp对应结构体的文件信息

    第20行,确认字库要写入Flash中的地址

    第21行,确认字库文件的大小

    第36行,从fftemp所指的字库文件中读取4096Bytes的数据到tempbuf缓冲区中,并且将当前读到数据的位置存入bread变量中

    第38行,将读到的4096Byte的字库数据写入Flash中

    第39行,字库的写入地址偏移增加

    第41行,判断字库数据是否已读取完

  • 相关阅读:
    MS SQL Server查询优化方法(收藏)
    .net打包并自动安装MS SQL Server数据库<转>
    解决oracle数据库监听器无法启动问题
    SQLServer2008/2005 /2000生成数据字典语句(转载)
    C# 常见错误处理(收藏)
    Oracle数据导入导出
    Oracle Database 9i/10g安装后的基本环境与服务
    Oracle to_char()函数的用法
    oracle参数列表
    SQL Server中存储过程比直接运行SQL语句慢的原因(转载)
  • 原文地址:https://www.cnblogs.com/skullboyer/p/7867605.html
Copyright © 2011-2022 走看看