zoukankan      html  css  js  c++  java
  • LCD12864的MSP430驱动程序(草稿)

    为解决原有指令集只能使全码反白,不能使单个字符的半码反白问题,写了单个字符反白和恢复函数。原理是:在DDRAM中写字符,然后在GDRAM中原字符位置写1,则该位置显示内容为GDRAM和DDRAM数据的异或,故字符显示反白;在GDRAM中原字符位置写0,清除掉GDRAM内容,则显示内容恢复。

    .c文件

    //=================================版本信息==================================//
    //Ver:2011082002
    //Author:XZQ
    //===========================================================================//
    #include "LCD12864_Driver.h"
    /*******************************************
    函数名称:Write_Cmd
    功    能:向液晶中写控制命令
    参    数:cmd--控制命令
    返回值  :无
    ********************************************/
    void Write_Cmd(uchar cmd)
    {
        uchar lcdtemp = 0;                    //定义一个变量为输出               
    			
        LCD_RS_L;                             //设置为命令输入/输出
        LCD_RW_H;                             //设置为读数据/命令
        LCD_DataIn;                           //设置P9口的方向为输入
        do                                    //判忙,直到不忙位置
        {    
            LCD_EN_H;                         //LCD使能
            delay_us(1);	                          //空操作				
           	lcdtemp = LCD2MCU_Data;           //将读到的数据放入lcdtemp
           	LCD_EN_L;                         //不选择LCD
            
        }
        while(lcdtemp & 0x80); 
        
        LCD_DataOut;    
        LCD_RW_L;  		
        MCU2LCD_Data = cmd; 
        LCD_EN_H;
        delay_us(1);						  			
        LCD_EN_L;
    }
    
    /*******************************************
    函数名称:Write_Data
    功    能:向液晶中写显示数据
    参    数:dat--显示数据
    返回值  :无
    ********************************************/
    void  Write_Data(uchar dat)
    {
        uchar lcdtemp = 0;   
            
        LCD_RS_L;
        LCD_RW_H;  
        LCD_DataIn;   
        do                         //判忙
        {    
            LCD_EN_H;
            delay_us(1);					
            lcdtemp = LCD2MCU_Data; 
            LCD_EN_L;      
        }
        while(lcdtemp & 0x80);  
        
        LCD_DataOut; 
        LCD_RS_H;
        LCD_RW_L;  
            
        MCU2LCD_Data = dat;
        LCD_EN_H;
        delay_us(1);	
        LCD_EN_L;
    } 
    /*******************************************
    函数名称:Read_Data
    功    能:读取液晶中的数据
    参    数:无
    返回值  :temp,读取的数据值
    ********************************************/
    uchar Read_Data()
    {
      uchar temp;	
      LCD_DataIn;
      LCD_RW_H;	//读数据,高电平有效
      LCD_EN_L;
      LCD_RS_H;  	//读数据,高电平有效
      delay_us(15);	//延时最小值1500ns 
      LCD_EN_H;	//lcden一旦拉高,数据开始读入
      temp=LCD2MCU_Data;//读出数据口的值		
      delay_us(15);	//读数据持续时间最小值1500ns
      LCD_EN_L;	//再次置低,准备下一次拉高
      LCD_DataOut;
      return temp;  //将读到的数据返回
    }
    /*******************************************
    函数名称:Ini_Lcd
    功    能:初始化液晶模块
    参    数:无
    返回值  :无
    ********************************************/
    void Ini_Lcd(void)
    {                  
        LCD_CMDOut;    //液晶控制端口设置为输出
        
        delay_ms(500);
        Write_Cmd(0x30);   //基本指令集
        delay_ms(1);
        Write_Cmd(0x02);   // 地址归位
        delay_ms(1);
    	Write_Cmd(0x0c);   //整体显示打开,游标关闭
        delay_ms(1);
    	Write_Cmd(0x01);   //清除显示
        delay_ms(1);
    	Write_Cmd(0x06);   //游标右移
        delay_ms(1);
    	Write_Cmd(0x80);   //设定显示的起始地址
    }
    /*******************************************
    函数名称:DispData8Bit
    功    能:将8位无符号二进制数以十进制方式显示
    参    数:uchar Data8Bit要显示的数据
              uchar addr 数据显示位置(0x80-0x98+7)
    返回值  :无
    ********************************************/
    void Disp8BitData(uchar Data8Bit,uchar addr)
    { 
      uchar bai=0,shi=0,ge=0;
      bai= Data8Bit/100;
      Write_Cmd(addr);
      Write_Data(bai+0x30);
      Data8Bit= Data8Bit%100;
      shi= Data8Bit/10;
      Write_Data(shi+0x30);
      ge= Data8Bit%10;
      Write_Data(ge+0x30);
    }
    /*******************************************
    函数名称:DispData16Bit
    功    能:将16位无符号二进制数以十进制方式显示
    参    数:uchar Data16Bit要显示的数据
              uchar addr 数据显示位置(0x80-0x98+7)
    返回值  :无
    ********************************************/
    void Disp16BitData(uint Data16Bit,uchar addr)
    { 
      uchar Bit5=0,Bit4=0,Bit3=0,Bit2=0,Bit1=0;
      
      Write_Cmd(addr);
      Bit5= Data16Bit/10000;
      Write_Data(Bit5+0x30);
      
      Data16Bit=Data16Bit%10000;
      Bit4= Data16Bit/1000;
      Write_Data(Bit4+0x30);
      
      Data16Bit=Data16Bit%1000;
      Bit3= Data16Bit/100;
      Write_Data(Bit3+0x30);
      
      Data16Bit=Data16Bit%100;
      Bit2= Data16Bit/10;
      Write_Data(Bit2+0x30);
      
      Bit1= Data16Bit%10;
      Write_Data(Bit1+0x30);
    }
    
    /*******************************************
    函数名称:Disp_HZ
    功    能:控制液晶显示汉字
    参    数:x:行坐标{0,1,2,3}
              y:列坐标[0-7]
              pt--指向显示数据的指针
              num--显示字符个数
    返回值  :无
    ********************************************/
    void Disp_HZ(uchar x,uchar y,const uchar * pt,uchar num)
    {
        uchar i;
        if (x==0)Write_Cmd(0x80+y);
        else if(x==1)Write_Cmd(0x90+y);	
        else if(x==2)Write_Cmd(0x88+y);
        else Write_Cmd(0x98+y);
        for(i = 0;i < (num*2);i++) 
          Write_Data(*(pt++)); 
    } 
    /*******************************************
    函数名称:Draw1Word
    功    能:打点。在液晶屏幕显示一次16位数据图像
    参    数:z;半屏坐标,0-上半屏,1-下半屏
             y:行坐标[0-31]
             x:列坐标[0-7]
             ByteData:要显示的图像数据高位在前,地位在后
    返回值  :无
    说明:坐标系示意  
          -----0---x---7----------
         |0
     z=0 |y
         |31
         |0
     z=1 |y
         |31
    ********************************************/
    void Draw1Word(uchar z,uchar y,uchar x,uint WordData)
    {
        Write_Cmd(0x34);        //打开扩展指令集           
       
        Write_Cmd(0x80+y);//设置行地址
        if(z==0) Write_Cmd(0x80+x);//设置半屏地址和列地址
        if(z==1) Write_Cmd(0x88+x);//设置半屏地址和列地址
        Write_Data((uint)(WordData>>8));
        Write_Data((uint)WordData);
      
        Write_Cmd(0x36);        //打开绘图显示
        Write_Cmd(0x30);        //回到基本指令集
    }
    /*******************************************
    函数名称:Clear_DDRAM
    功    能:清除液晶DDRAM中的随机数据
    参    数:无
    返回值  :无
    ********************************************/
    void Clear_DDRAM()
    {
      uchar i;
      Write_Cmd(0x30);//打开基本指令集
      Write_Cmd(0x80);
      for(i=0;i<32;i++)
        Write_Data(' ');
      Write_Cmd(0x90);
      for(i=0;i<32;i++)
        Write_Data(' ');
    }
    /*******************************************
    函数名称:Clear_GDRAM
    功    能:清除液晶GDRAM中的随机数据
    参    数:无
    返回值  :无
    ********************************************/
    void Clear_GDRAM(void)
    {
        uchar i,j,k;
        
    	Write_Cmd(0x34);        //打开扩展指令集
    	i = 0x80;            
    	for(j = 0;j < 32;j++)
    	{
            Write_Cmd(i++);
            Write_Cmd(0x80);
      		for(k = 0;k < 16;k++)
      		{
      		    Write_Data(0x00);
      		}
    	}
    	i = 0x80;
     	for(j = 0;j < 32;j++)
    	{
     	    Write_Cmd(i++);
            Write_Cmd(0x88);	   
      		for(k = 0;k < 16;k++)
      		{
       		    Write_Data(0x00);
       		} 
    	}   
    	Write_Cmd(0x30);        //回到基本指令集
    }
    /*******************************************
    函数名称:Draw_PM
    功    能:在整个液晶屏幕上画图
    参    数:无
    返回值  :无
    ********************************************/
    void Draw_PM(const uchar *ptr)
    {
        uchar i,j,k;
        
    	Write_Cmd(0x34);        //打开扩展指令集
    	i = 0x80;            
    	for(j = 0;j < 32;j++)
    	{
            Write_Cmd(i++);
            Write_Cmd(0x80);
      		for(k = 0;k < 16;k++)
      		{
      		    Write_Data(*ptr++);
      		}
    	}
    	i = 0x80;
     	for(j = 0;j < 32;j++)
    	{
     	Write_Cmd(i++);
            Write_Cmd(0x88);	   
      		for(k = 0;k < 16;k++)
      		{
       		    Write_Data(*ptr++);
       		} 
    	}  
        Write_Cmd(0x36);        //打开绘图显示
    	Write_Cmd(0x30);        //回到基本指令集
    }
    /*******************************************
    函数名称: Lcd_set_dot
    功    能:ST7920控制的12864任意位置打点函数
    参    数:uchar x,uchar y,坐标点,范围x[0:127],y[0:63]
    返回值  :无
    说明:坐标系示意  
          -----0---x---127----------
         |0
         |y
         |63
    ********************************************/
    void Lcd_set_dot(uchar x,uchar y)
    {
      uchar x_byte,x_bit;	//确定dot在横轴上的哪个字节内的哪个位
      uchar y_byte,y_bit;	//确定dot在竖轴上的哪个字节内的哪个位
      uchar TempH,TempL;	//用来存放读出来的原始数据的高8位和低8位,
    			//目的是为了避免新的数据点写进去后覆盖掉前面的点
    
      x=x&0x7f;		//限制横坐标所在范围,为0-127
      y=y&0x3f;		//限制纵坐标所在范围,为0-31(上半屏)  32-63(下半屏)
    
      x_byte=x/16;		//确定该dot在哪一个字节	
      x_bit=x%16;		//确定该dot在哪一个点
      y_byte=y/32;		//确定该dot在那个半屏,0:上半屏 1:下半屏 
      y_bit=y%32;		//确定该dot在第几行(因为到了下半屏也是从0行开始到31行)
    	
      Write_Cmd(0x34);			//打开扩展指令集,关闭基本功能模式,绘图显示关闭
      Write_Cmd(0x80+y_bit);		//先将光标纵坐标写到指定行
      Write_Cmd(0x80+x_byte+8*y_byte);	//再将光标横坐标写到指定位置,若y_byte为1,则说明大于了31行(从0行算起)
    					//则需将AC指针写到0x88处即ST7920控制下的第3行
      
      Read_Data();               //当下设定AC地址指令后,若要读取数据需要预先dummy read一次,才会读到正确数据
    	  		     //第2次读取时不需要dummy read,除非又重新设定AC位置才需再次dummy read
    
      TempH=Read_Data();			//读取高8位数据
      TempL=Read_Data();			//读取低8位数据											
    	
      Write_Cmd(0x80+y_bit);		//读操作会改变AC位置,所以需要重新写入1次
      Write_Cmd(0x80+x_byte+8*y_byte);	
    
      if(x_bit<8)
      {
        Write_Data(TempH|(0x01<<(7-x_bit))); //如果要写的dot在高8位,则这样写利用or运算避免新数据覆盖原先数据
        Write_Data(TempL);			//原先的低8位数据照常写入
      }
      else
      {
        Write_Data(TempH);						//如果要写的dot在低8位,原先的高8位数据照常写入
        Write_Data(TempL|(0x01<<(15-x_bit)));	//低8位则这样写利用or运算避免新数据覆盖原先数据
      }
    		
      Write_Cmd(0x36);		//开绘图显示									
      Write_Cmd(0x30);		//回到GDRAM显示模式
    }
    /*******************************************
    函数名称: CharHighlight
    功    能:让显示的单个字符反白显示或恢复显示
    参    数:uchar x,uchar y,uchar flag.
            坐标点范围x[0:15],y[0:3],
             flag=0显示恢复,flag=1反白显示。
    返回值  :无
    说明:坐标系示意  
          -----0---x---15----------
         |0
         |y
         |3
    注意:全码内的两个字符只有一个可以反白显示。恢复全码内的一个
          字符,则全码内两个字符同时恢复。此函数随不完善,但已符合
          数字输入提示显示。
    ********************************************/
    void  CharHighlight(uchar x,uchar y,uchar flag)
    {
      uchar z,x1,y1,i;
      uint  WordData;
      switch(y)
      {
        case 0:y1=0;break;
        case 1:y1=16;break;
        case 2:y1=0;break;
        case 3:y1=16;break;
        default:y1=0;
      }
      if(y<2)z=0;
      else z=1;
      if(flag==0)WordData=0;
      else
      {
          if(x%2==0) WordData=0xFF00;
          else WordData=0x00FF;
      }
      x1=x/2;
      
      for(i=0;i<16;i++)
      {
          Draw1Word( z,y1+i, x1, WordData);
      }
    }
    /************************************鉴相器频率显示****************************/
    void Disp_f(uint Data16Bit,uchar addr)
    {
      uint FreValue=0;
      FreValue=150000/Data16Bit;
      Disp16BitData(FreValue,addr);
    }
    void Disp_Pha(uint Data16Bit1,uint Data16Bit2,uchar addr)
    {
      float Pha=0;
      uchar PhaValue=0;
      Pha=Data16Bit2/Data16Bit1;
      PhaValue=(uint)Pha*100;
      Disp8BitData(PhaValue,addr);
    }
    /*******************************************
    函数名称:DispData16Bit
    功    能:将16位无符号二进制数以十进制方式显示
    参    数:uchar Data16Bit要显示的数据
              uchar addr 数据显示位置(0x80-0x98+7)
    返回值  :无
    ********************************************/
    void DispFre(long int Data16Bit,uchar addr)
    { 
      uchar Bit6,Bit5=0,Bit4=0,Bit3=0,Bit2=0,Bit1=0;
      
      Write_Cmd(addr);
      Bit6= Data16Bit/100000;
      Write_Data(Bit6+0x30);
      Data16Bit%=100000;
      
      Bit5= Data16Bit/10000;
      Write_Data(Bit5+0x30);
      
      Data16Bit=Data16Bit%10000;
      Bit4= Data16Bit/1000;
      Write_Data(Bit4+0x30);
      
      Write_Data(',');
      
      Data16Bit=Data16Bit%1000;
      Bit3= Data16Bit/100;
      Write_Data(Bit3+0x30);
      
      Data16Bit=Data16Bit%100;
      Bit2= Data16Bit/10;
      Write_Data(Bit2+0x30);
      
      Bit1= Data16Bit%10;
      Write_Data(Bit1+0x30);
      
      Write_Data('H');
    }
    
    /************************************ADC12数据显示****************************/
    void DispVoltage(uint VolValue,uchar Addr)
    {
      uint Value=0,Data16Bit;
      uchar Bit4=0,Bit3=0,Bit2=0,Bit1=0;
      Value=(uint)VolValue*3.3*1000/4055;
      
      Data16Bit=Value;
      Write_Cmd(Addr);
      
      Data16Bit=Data16Bit%10000;
      Bit4= Data16Bit/1000;
      Write_Data(Bit4+0x30);
      
      Write_Data('.');
      
      Data16Bit=Data16Bit%1000;
      Bit3= Data16Bit/100;
      Write_Data(Bit3+0x30);
      
      Data16Bit=Data16Bit%100;
      Bit2= Data16Bit/10;
      Write_Data(Bit2+0x30);
      
      Bit1= Data16Bit%10;
      Write_Data(Bit1+0x30);
      
      Write_Data('V');
    }
    
    .h文件
    //=================================版本信息==================================//
    //Ver:2011082002
    //Author:XZQ
    //===========================================================================//
    #ifndef _LCD12864_DRIVER_H
    #define _LCD12864_DRIVER_H
    //=================================头文件=================================//
    #include <msp430f5438.h>
    #include "MCU_Init.h"
    //=================================引脚分配===============================//
    //数据线
    #define LCD_DataIn     P3DIR=0x00            //设置数据方向为输入
    #define LCD_DataOut    P3DIR=0xFF            //设置数据传输方向为输出
    #define LCD2MCU_Data   P3IN                  //将LCD的数据放入MCU
    #define MCU2LCD_Data   P3OUT                 //将MCU的输出数据放入LCD
    //控制线 
    #define LCD_CMDOut     P7DIR|=BIT6+BIT5+BIT4;
    #define LCD_RS_H       P7OUT|=BIT4          //P8.0至高, 
    #define LCD_RS_L       P7OUT&=~BIT4          //P8.0至低,进行命令传输
    #define LCD_RW_H       P7OUT|=BIT5          //P8.1至高
    #define LCD_RW_L       P7OUT&=~BIT5          //P8.1至低
    #define LCD_EN_H       P7OUT|=BIT6          //P8.2至高,控制使能为正
    #define LCD_EN_L       P7OUT&=~BIT6          //P8.2至低,控制使能为负
    //=================================函数申明===============================//
    //底层驱动函数
    extern void Write_Cmd(unsigned char cod);
    extern void Write_Data(unsigned char dat);
    extern uchar Read_Data(void);
    //基本功能函数
    extern void Ini_Lcd(void);
    extern void Clear_GDRAM(void);
    extern void Clear_DDRAM(void);
    extern void Draw_PM(const unsigned char *ptr); 
    //高级功能函数
    extern void Disp8BitData(uchar Data8Bit,uchar addr);
    extern void Disp16BitData(uint Data16Bit,uchar addr);
    extern void Disp_HZ(uchar x,uchar y,const uchar * pt,uchar num);
    extern void Draw1Word(uchar z,uchar x,uchar y,uint WordData);
    extern void Lcd_set_dot(uchar x,uchar y);
    //单个字符反白或恢复显示函数
    extern void Draw1Word(uchar z,uchar x,uchar y,uint WordData);
    void  CharHighlight(uchar x,uchar y,uchar flag);
    //其他外设数据显示函数
    extern void Disp_f(uint Data16Bit,uchar addr);
    extern void Disp_Pha(uint Data16Bit1,uint Data16Bit2,uchar addr);
    extern void DispFre(long int FreValue,uchar addr);
    extern void DispVoltage(uint VolValue,uchar Addr);
    
    #endif 
    

  • 相关阅读:
    Hibernate映射之数组属性, 集合属性(list、set和map)
    org.hibernate.type.SerializationException: could not deserialize 反序列化失败
    linux下同一个tomcat部署多个项目
    Nexus私服 Maven
    maven 父子项目 聚合与继承 生命周期 打包插件 依赖打包 jar pom war
    IDEA中创建Web聚合项目(Maven多模块项目)
    为什么要在linux命令前加上 ./ 什么时候才需要在命令前加上./
    web.xml 介绍 and pom.xml 介绍
    有趣的linux命令
    SpringMVC 中常见注释
  • 原文地址:https://www.cnblogs.com/yuesheng/p/2147583.html
Copyright © 2011-2022 走看看