为何此程序在PIC16F914上1602上显示不正常
[复制链接]
显示很暗很暗--全是大黑快--此程序只需改一点点配置(ADCON1和ANSEL处),却可以在877A上面显示正常。
#include <htc.h> #define uchar unsigned char #define uint unsigned int #define TESTBIT(a,b) ((a)&(1<<(b))) __CONFIG(WDTDIS & HS & PWRTDIS & BORDIS);//设置配置位
#define LCD_RS RA0 #define LCD_RW RA1 #define LCD_EN RA2
/************************定义显示字符*****************************************/ uchar Wel[] = {"Welcome To BeiJin"}; uchar tab[] = {"0123456789"}; /************************声明函数*********************************************/ void Delay_US(uint delay); void Delay_Ms(uint delay); void Delay_Sec(uint delay); uchar Chk_1602_busy(void); void Write_1602_command(uchar gcmd,uchar gvalue); void Write_1602_data(uchar gdata); void INIT_1602(void); void Display_1602_string(uchar gadd_start,uchar gline,uchar glength,uchar *pdata); void Display_1602(uchar x,uchar y,uchar gdata); void Clear_Display(void); void Open_Disp(void); void Close_Disp(void); /******************************************************************************* * 函 数 名: Delay_US(uint8 delay) * 函数功能: 微秒延时--12us * 入口参数: delay * 返 回: 无 *******************************************************************************/ void Delay_US(uint delay) { for(;delay;) { delay--; } } /******************************************************************************* * 函 数 名: Delay_MS(uint16 delay) * 函数功能: 毫秒延时--1ms * 入口参数: delay * 返 回: 无 *******************************************************************************/ void Delay_Ms(uint delay) { uint i; for(i=0;i<delay;i++) Delay_US(83); } /******************************************************************************* * 函 数 名: Delay_Sec(uint16 delay) * 函数功能: 毫秒延时--1ms * 入口参数: delay * 返 回: 无 *******************************************************************************/ void Delay_Sec(uint delay) { uint i,j; for(i=0;i<20*delay;i++) { for(j=0;j<4536;j++); } } /******************************************************************************* * 函 数 名: Read_LCD_Busy(void) * 函数功能: 读液晶忙通道数据 * 入口参数: 无 * 返 回: 无 *******************************************************************************/ uchar Chk_1602_busy(void) { uint gR_data; uint gwait_time=0xff; //设置忙超时数 LCD_RS=0; //表示状态 LCD_RW=1; //选择读 LCD_EN=1; TRISC = 0xFF; //接收口设为输入口 Delay_US(30); gR_data=PORTC; while(TESTBIT(gR_data,7)) //表示busy { --gwait_time; if(!gwait_time) { LCD_EN=0;TRISC = 0x00; return 0; } } LCD_EN=0; TRISC = 0x0; //恢复为输出口 return 1; } /****************************************************************************** * 函 数 名: Write_LCD_Comd(uint8 commond) * 函数功能: 写指令 * 入口参数: commond指令 * 返 回: 无 *******************************************************************************/ void Write_1602_command(uchar gcmd,uchar gvalue) { if(gvalue) //写命令时大部分情况下是在LCD空闲模式下写 { if(Chk_1602_busy()) { LCD_RS=0; //选择指令 LCD_RW=0; //选择写 PORTC=gcmd; //赋指令 LCD_EN=1; //使能 Delay_US(30); LCD_EN=0; } } else { LCD_RS=0; //选择指令 LCD_RW=0; //选择写 PORTC=gcmd; //赋指令 LCD_EN=1; //使能 Delay_US(30); LCD_EN=0; } } /****************************************************************************** * 函 数 名: Write_LCD_Data(uint8 Data) * 函数功能: 写数据 * 入口参数: Data数据 * 返 回: 无 *******************************************************************************/ /*----------- 写数据 -------------*/ void Write_1602_data(uchar gdata) { if(Chk_1602_busy()) //写数据必须是在LCD空闲模式下才能写 { LCD_RS=1; //选择数据 LCD_RW=0; //选择写 PORTC=gdata; LCD_EN=1; //使能 Delay_US(30); LCD_EN=0; Delay_US(10); } } /****************************************************************************** * 函 数 名: LCD1602_Init(void) * 函数功能: 初始化1602LCD * 入口参数: 无 * 返 回: 无 *******************************************************************************/ /*-----------1602初始化函数-------------*/ void INIT_1602(void) { Delay_Ms(15); Write_1602_command(0x38,0); //设置16X2显示,5X7点阵,8位数据传送,不检测忙信号 Delay_Ms(5); Write_1602_command(0x38,0); Delay_Ms(5); Write_1602_command(0x38,0); //设置16X2显示,5X7点阵,8位数据传送,不检测忙信号 Write_1602_command(0x38,1); //设置16X2显示,5X7点阵,8位数据传送,检测忙信号 Write_1602_command(0x08,1); //关闭显示、无光标、检测忙信号 Write_1602_command(0x01,1); //清屏、光标归位、AC=0、检测忙信号 Write_1602_command(0x06,1); //显示光标右移位置、检测忙信号 Write_1602_command(0x0c,1); //显示功能开、无光标 } /****************************************************************************** * 函 数 名: void Display_1602_string(uchar gadd_start,uchar gline,uchar glength,uchar *pdata) * 函数功能: 显示字符串 * 入口参数: gadd_start-列号,uchar gline-行号,glength-数据长度,pdata-数组元素 * 返 回: 无 *******************************************************************************/ /*-----------显示字符串-------------*/ // 列号 行号 数据长度 数组元素 void Display_1602_string(uchar gadd_start,uchar gline,uchar glength,uchar *pdata) { uchar gaddress; uchar *pdat; uchar gcount=0; if(!gline) //第0行 { gaddress=0x80+gadd_start; } //地址对应 else { gaddress=0xc0+gadd_start; } //第一行 for(;gcount<glength;gcount++) { Write_1602_command(gaddress,1); //设定数据地址 Write_1602_data(*pdata); //取设定地址里的数据 gaddress++; pdata++; } } /*-----------指定位置显示字符-------------*/ void Display_1602(uchar x,uchar y,uchar gdata) { uchar gaddress; if(y) { gaddress=0x80+x; } else { gaddress=0xc0+x; } Write_1602_command(gaddress,1); //设定数据地址 Write_1602_data(gdata); } /*-----------清屏-------------*/ void Clear_Display(void) { Write_1602_command(0x01,1); Delay_Ms(5); } void Open_Disp(void) { Write_1602_command(0x0c,1); } void Close_Disp(void) { Write_1602_command(0x08,1); }
/****************************************************************************** * 函 数 名: main() * 函数功能: LCD显示字符 * 入口参数: 无 * 返 回: 无 *******************************************************************************/ void main() { ANSEL = 0x00; //ADCON1 = 0x87; //设置PORTA为普通IO口 TRISA0 = 0; TRISA1 = 0; TRISA2 = 0; TRISA3 = 0; TRISC = 0x00; //设置PORTC为输出 Delay_Ms(10); INIT_1602(); Delay_Ms(100); while(1) { RA3 = 1;Delay_Ms(1000);RA3 = 0; Display_1602_string(0,0,16,tab); RA3 = 0;Delay_Ms(1000);RA3 = 1; } }
|