需要有个技术小结,为此做了一个PID温度控制器,要求入下:
1. 使用LCD1602显示:测量温度、设置温度、控制状态、输出量等。 2. 使用STC15W408AS单片机做为主控制系统。 3. 使用NTC电阻测量温度,经单片机取样后转换为温度显示。 4. 通过E,ADD,SUB三个输入按键修改设置温度、手动/自动、控制参数、输出量等。以1秒为周期,输出PWM波控制MOS管调节发热板的温度
电路图:
电路图
主要使用指令:
程序流程图:
单片机函数:
/* 硬件说明: 1.使用STC15W408AS单片机,使用内部IRS时钟30MHz。 2.使用LCD1602显示,P2口输出8位并口数据,P3.2设置指令/数据,P3.3下降沿执行。 3.P1.1模拟量输入端,P1.3按键E,P1.4按键SUB,P1.5按键ADD。 4.P1.0PWM输出。
程序运行说明: 1.每1毫秒执行1次程序。 2.温度测量范围0--110度,精度1度。1000个温度平均1次,1秒更新1次温度值。 3.通过按键E激活或选择菜单,按键SUB和ADD修改参数,并具有保存设置参数到EEPROM功能。 按键连续加减时每50毫秒加减1次,激活显示消影取消影项最后一个数值以10个输出为1周期,一半显示一半消影。 4.PWM以1000毫秒(1秒)为周期,最小1毫秒。 5.LCD每1毫秒执行1个指令或数据。
*/
#include<stc15w408as.h>//头文件
//主函数+初始化+计时-------------------------------------------------------------- void INIT();//初始化函数 void T_00();//计时函数 unsigned int T_1S;//1秒计时器
//NTC_01温度-------------------------------------------------------------- void NTC_01();//温度 unsigned int ADC_IN,NTC_PV;//模拟量,温度和缓存 unsigned long int PV_BUF;//温度累积值
//ADC数值40-790对应0-111度, NTC 10K 3950电阻10K取样电阻转换值 unsigned char code NTC_DATA[]={ 0X6F,0X6F,0X6F,0X6F,0X6F,0X6F,0X6F,0X6F,0X6E,0X6E,0X6D,0X6C,0X6B,0X6B,0X6A,0X6A,0X69,0X68,0X68,0X67 ,0X67,0X66,0X65,0X65,0X64,0X64,0X63,0X63,0X62,0X62,0X61,0X61,0X60,0X60,0X5F,0X5F,0X5E,0X5E,0X5D,0X5D ,0X5C,0X5C,0X5B,0X5C,0X5A,0X5A,0X5A,0X59,0X59,0X58,0X58,0X58,0X57,0X57,0X56,0X56,0X56,0X55,0X55,0X55 ,0X54,0X54,0X54,0X53,0X53,0X53,0X52,0X52,0X52,0X51,0X51,0X51,0X50,0X50,0X50,0X4F,0X4F,0X4F,0X4F,0X4E ,0X4E,0X4E,0X4D,0X4D,0X4D,0X4D,0X4C,0X4C,0X4C,0X4C,0X4B,0X4B,0X4B,0X4B,0X4A,0X4A,0X4A,0X4A,0X49,0X49 ,0X49,0X49,0X48,0X48,0X48,0X48,0X47,0X47,0X47,0X47,0X46,0X46,0X46,0X46,0X45,0X45,0X45,0X45,0X45,0X44 ,0X44,0X44,0X44,0X43,0X43,0X43,0X43,0X43,0X43,0X42,0X42,0X42,0X42,0X42,0X41,0X41,0X41,0X41,0X40,0X40 ,0X40,0X40,0X40,0X40,0X3F,0X3F,0X3F,0X3F,0X3F,0X3E,0X3E,0X3E,0X3E,0X3E,0X3E,0X3D,0X3D,0X3D,0X3D,0X3D ,0X3D,0X3C,0X3C,0X3C,0X3C,0X3C,0X3C,0X3B,0X3B,0X3B,0X3B,0X3B,0X3B,0X3B,0X3A,0X3A,0X3A,0X3A,0X3A,0X39 ,0X39,0X39,0X39,0X39,0X39,0X39,0X38,0X38,0X38,0X38,0X38,0X38,0X37,0X37,0X37,0X37,0X37,0X37,0X37,0X36 ,0X36,0X36,0X36,0X36,0X36,0X36,0X35,0X35,0X35,0X35,0X35,0X35,0X35,0X34,0X34,0X34,0X34,0X34,0X34,0X34 ,0X33,0X33,0X33,0X33,0X33,0X33,0X33,0X32,0X32,0X32,0X32,0X32,0X32,0X32,0X32,0X31,0X31,0X31,0X31,0X31 ,0X31,0X31,0X31,0X30,0X30,0X30,0X30,0X30,0X30,0X30,0X30,0X2F,0X2F,0X2F,0X2F,0X2F,0X2F,0X2F,0X2F,0X2E ,0X2E,0X2E,0X2E,0X2E,0X2E,0X2E,0X2E,0X2E,0X2D,0X2D,0X2D,0X2D,0X2D,0X2D,0X2D,0X2D,0X2C,0X2C,0X2C,0X2C ,0X2C,0X2C,0X2C,0X2C,0X2C,0X2B,0X2B,0X2B,0X2B,0X2B,0X2B,0X2B,0X2B,0X2A,0X2A,0X2A,0X2A,0X2A,0X2A,0X2A ,0X2A,0X2A,0X29,0X29,0X29,0X29,0X29,0X29,0X29,0X29,0X29,0X29,0X28,0X28,0X28,0X28,0X28,0X28,0X28,0X28 ,0X28,0X27,0X27,0X27,0X27,0X27,0X27,0X27,0X27,0X27,0X26,0X26,0X26,0X26,0X26,0X26,0X26,0X26,0X26,0X26 ,0X25,0X25,0X25,0X25,0X25,0X25,0X25,0X25,0X25,0X25,0X24,0X24,0X24,0X24,0X24,0X24,0X24,0X24,0X24,0X24 ,0X23,0X23,0X23,0X23,0X23,0X23,0X23,0X23,0X23,0X23,0X22,0X22,0X22,0X22,0X22,0X22,0X22,0X22,0X22,0X22 ,0X21,0X21,0X21,0X21,0X21,0X21,0X21,0X21,0X21,0X21,0X21,0X20,0X20,0X20,0X20,0X20,0X20,0X20,0X20,0X20 ,0X20,0X1F,0X1F,0X1F,0X1F,0X1F,0X1F,0X1F,0X1F,0X1F,0X1F,0X1F,0X1E,0X1E,0X1E,0X1E,0X1E,0X1E,0X1E,0X1E ,0X1E,0X1E,0X1E,0X1D,0X1D,0X1D,0X1D,0X1D,0X1D,0X1D,0X1D,0X1D,0X1D,0X1C,0X1C,0X1C,0X1C,0X1C,0X1C,0X1C ,0X1C,0X1C,0X1C,0X1C,0X1C,0X1B,0X1B,0X1B,0X1B,0X1B,0X1B,0X1B,0X1B,0X1B,0X1B,0X1B,0X1B,0X1A,0X1A,0X1A ,0X1A,0X1A,0X1A,0X1A,0X1A,0X1A,0X19,0X19,0X19,0X19,0X19,0X19,0X19,0X19,0X19,0X19,0X19,0X19,0X19,0X19 ,0X18,0X18,0X18,0X18,0X18,0X18,0X18,0X18,0X18,0X17,0X17,0X17,0X17,0X17,0X17,0X17,0X17,0X17,0X17,0X17 ,0X16,0X16,0X16,0X16,0X16,0X16,0X16,0X16,0X16,0X16,0X16,0X16,0X16,0X15,0X15,0X15,0X15,0X15,0X15,0X15 ,0X15,0X15,0X15,0X15,0X15,0X14,0X14,0X14,0X14,0X14,0X14,0X14,0X14,0X14,0X14,0X13,0X13,0X13,0X13,0X13 ,0X13,0X13,0X13,0X13,0X13,0X13,0X13,0X12,0X12,0X12,0X12,0X12,0X12,0X12,0X12,0X12,0X12,0X11,0X11,0X11 ,0X11,0X11,0X11,0X11,0X11,0X11,0X11,0X11,0X11,0X10,0X10,0X10,0X10,0X10,0X10,0X10,0X10,0X10,0X10,0X10 ,0X0F,0X0F,0X0F,0X0F,0X0F,0X0F,0X0F,0X0F,0X0F,0X0F,0X0F,0X0F,0X0E,0X0E,0X0E,0X0E,0X0E,0X0E,0X0E,0X0E ,0X0E,0X0E,0X0E,0X0D,0X0D,0X0D,0X0D,0X0D,0X0D,0X0D,0X0D,0X0D,0X0D,0X0D,0X0C,0X0C,0X0C,0X0C,0X0C,0X0C ,0X0C,0X0C,0X0C,0X0C,0X0C,0X0B,0X0B,0X0B,0X0B,0X0B,0X0B,0X0B,0X0B,0X0B,0X0B,0X0B,0X0A,0X0A,0X0A,0X0A ,0X0A,0X0A,0X0A,0X0A,0X0A,0X0A,0X0A,0X09,0X09,0X09,0X09,0X09,0X09,0X09,0X09,0X09,0X09,0X09,0X08,0X08 ,0X08,0X08,0X08,0X08,0X08,0X08,0X08,0X08,0X08,0X08,0X07,0X07,0X07,0X07,0X07,0X07,0X07,0X07,0X07,0X07 ,0X06,0X06,0X06,0X06,0X06,0X06,0X06,0X06,0X06,0X06,0X05,0X05,0X05,0X05,0X05,0X05,0X05,0X05,0X05,0X05 ,0X04,0X04,0X04,0X04,0X04,0X04,0X04,0X04,0X04,0X04,0X03,0X03,0X03,0X03,0X03,0X03,0X03,0X03,0X03,0X03 ,0X03,0X02,0X02,0X02,0X02,0X02,0X02,0X02,0X02,0X02,0X01,0X01,0X01,0X01,0X01,0X01,0X01,0X01,0X01,0X01 ,0X01,0X00,0X00,0X00,0X00,0X00,0X00,0X00,0X00,0X00,0X00};
//SW_02按键-------------------------------------------------------------- void SW_02();//按键 sbit SW_E=P1^3;//按键E sbit SW_SUB=P1^4;//按键SUB sbit SW_ADD=P1^5;//按键ADD unsigned char SW_E_T,SW_SUB_T,SW_ADD_T;//按键计时器 unsigned char SW_M;//菜单激活激活计数器 unsigned int SW_M_T;//菜单激活计时器
//PID_03控制-------------------------------------------------------------- void PID_03();//控制 sbit PWM_OUT=P1^0;//PWM输出端口 unsigned char PID_PV,PID_SV,PID_MA,PID_P,PID_I;//设置计数器 unsigned char PID_V,PID_I_T;//温度差,积分计时器 int PID_OUT,PID_I_BUF;//输出计数器
//LCD_04显示-------------------------------------------------------------- void LCD_04();//显示 #define LCD_DATA P2 //8位并口 sbit LCD_RS=P3^2;//指令/数据设置 sbit LCD_E=P3^3;//下降沿执行 unsigned char LCD_C,LCD_ON;//计数器,消影计数器 unsigned char code LCD_INIT[]={0X38,0X06,0X0C,0X01};//8位,显示开,增量,清屏 unsigned char LCD_BUF[]="#PV:123 OUT:123.4#SV:123 M* P:12.3";//缓冲区 unsigned char LCD_CHAR[]="0123456789 MA*PI:.";//字符显示
//声明结束。。。。。。。。。。。。。。。。。。。。。。。。。。。。。
//主函数+初始化+计时-------------------------------------------------------------- void main()//主函数 { INIT();//初始化 while(1)//循环指令 { while(!TF0);//1毫秒溢出等待,复位溢出标记 TF0=0;
T_00();//T_00计时 NTC_01();//NTC_01温度 SW_02();//SW_02按键 PID_03();//PID_03控制 LCD_04();//LCD_04显示 } } void INIT()//初始化函数 { //T0,12T/30M=0.4us;0.4*2500=1ms. AUXR&=0X80;//B7=1,T0=12T TMOD&=0XF0;//B3210=0;//内计数,计时器,16位自动重装 TL0=(65536-2500)%256;//重装值低8位 TH0=(65536-2500)/256;//重装值高8位 TF0=0;//T0溢出标记复位 TR0=1;//T0开始计时
//ADC端口 P1ASF=0X02;//P1.1设置位模拟量输入 //读EEPROM IAP_CONTR=0X80;//允许IAP IAP_CMD=1;//读模式 IAP_ADDRH=0X00;//EEPROM地址高8位 IAP_ADDRL=0X00;//EEPROM地址低8位 IAP_TRIG=0X5A; IAP_TRIG=0XA5;//执行指令 while(0);//不循环,等待1个时钟 PID_SV=IAP_DATA;//读SV
IAP_ADDRL=0X01;//EEPROM地址低8位 IAP_TRIG=0X5A; IAP_TRIG=0XA5;//执行指令 while(0);//不循环,等待1个时钟 PID_MA=IAP_DATA;//读MA
IAP_ADDRL=0X02;//EEPROM地址低8位 IAP_TRIG=0X5A; IAP_TRIG=0XA5;//执行指令 while(0);//不循环,等待1个时钟 PID_P=IAP_DATA;//读P
IAP_ADDRL=0X03;//EEPROM地址低8位 IAP_TRIG=0X5A; IAP_TRIG=0XA5;//执行指令 while(0);//不循环,等待1个时钟 PID_I=IAP_DATA;//读I
IAP_CONTR=0;//关闭IAP IAP_CMD=0;//待机模式 IAP_ADDRH=0XFF;//设置到非EEPROM地址 IAP_ADDRL=0XFF;//设置到非EEPROM地址 IAP_TRIG=0;//清除触发寄存器
//LCD LCD_RS=0;//指令模式 for(LCD_C=0;LCD_C<4;LCD_C++)//发送4个设置参数 { LCD_DATA=LCD_INIT[LCD_C];//发送参数 LCD_E=1;//执行准备 LCD_E=0;//执行参数 while(!TF0);//等待1毫秒溢出 TF0=0;//溢出复位 } LCD_C=0;//复位计数器 LCD_BUF[0]=0X80;//缓冲区0是LCD第一行起始地址 LCD_BUF[17]=0XC0;//缓冲区17是LCD第二行起始地址 } void T_00()//计时函数 { //1秒循环计时 T_1S++;//1毫秒加1 if(T_1S>=1000)//计时满1000毫秒复位 T_1S=0; }
//NTC_01温度-------------------------------------------------------------- void NTC_01()//温度 { //设置ADC端口读 ADC_CONTR=0XE9;//启动ADC //读ADC数值 ADC_IN=ADC_RES;//高8位 ADC_IN=ADC_IN<<2;//左移2位 ADC_IN+=ADC_RESL;//低2位 //限制 if(ADC_IN<40) ADC_IN=40; if(ADC_IN>790) ADC_IN=790; //ADC转温度 NTC_PV=NTC_DATA[ADC_IN-40]; //温度累积 PV_BUF=PV_BUF+NTC_PV; //满1000个温度数据平均并复位 if(T_1S==0) { PV_BUF=PV_BUF/1000; PID_PV=PV_BUF; } }
//SW_02按键-------------------------------------------------------------- void SW_02()//按键 { //按键输入计时 if(SW_E==0&SW_E_T<200)//按键有输入且计时器小于200毫秒计时器加1 SW_E_T++; if(SW_E==1)//按键无输入 SW_E_T=0;//计时器复位 if(SW_SUB==0&SW_SUB_T<200)//按键有输入且计时器小于200毫秒计时器加1 SW_SUB_T++; if(SW_SUB==1)//按键无输入 SW_SUB_T=0;//计时器复位 if(SW_ADD==0&SW_ADD_T<200)//按键有输入且计时器小于200毫秒计时器加1 SW_ADD_T++; if(SW_ADD==1)//按键无输入 SW_ADD_T=0;//计时器复位 //按键E处理 if(SW_M==0&SW_E_T==200)//菜单未激活且按键E有连续200毫秒输入 { //计时器未满 if(SW_M_T<3000)//计时加1 SW_M_T++; else//计时器已满 { SW_M=1;//激活菜单 SW_M_T=10000;//计数器置数 } } if(SW_M>0)//菜单已激活操作 { //菜单循环选择 if(SW_E_T==10)//10毫秒防抖操作1次 { SW_M++;//菜单选择下1个 if(SW_M>5)//选择到I后回到OUT SW_M=1; } //计数器到数 SW_M_T--;//倒计时 if(SW_E_T>10|SW_SUB_T>10|SW_ADD_T>10)//按键有输入 SW_M_T=10000;//计数器置数 //计时器结束 if(SW_M_T==0) { SW_M=0;//关闭菜单
//保存设置到EEPROM //差除扇区 IAP_CONTR=0X80;//允许IAP IAP_CMD=3;//删除模式 IAP_ADDRH=0X00;//EEPROM地址高8位 IAP_ADDRL=0X00;//EEPROM地址低8位 IAP_TRIG=0X5A; IAP_TRIG=0XA5;//执行指令 while(0);//不循环,等待1个时钟 //写入设置到EEPROM IAP_CMD=2;//写模式 IAP_ADDRL=0X00;//EEPROM地址低8位 IAP_DATA=PID_SV;//写入SV IAP_TRIG=0X5A; IAP_TRIG=0XA5;//执行指令 while(0);//不循环,等待1个时钟
IAP_ADDRL=0X01;//EEPROM地址低8位 IAP_DATA=PID_MA;//写入MA IAP_TRIG=0X5A; IAP_TRIG=0XA5;//执行指令 while(0);//不循环,等待1个时钟
IAP_ADDRL=0X02;//EEPROM地址低8位 IAP_DATA=PID_P;//写入P IAP_TRIG=0X5A; IAP_TRIG=0XA5;//执行指令 while(0);//不循环,等待1个时钟
IAP_ADDRL=0X03;//EEPROM地址低8位 IAP_DATA=PID_I;//写入I IAP_TRIG=0X5A; IAP_TRIG=0XA5;//执行指令 while(0);//不循环,等待1个时钟
IAP_CONTR=0;//关闭IAP IAP_CMD=0;//待机模式 IAP_ADDRH=0XFF;//设置到非EEPROM地址 IAP_ADDRL=0XFF;//设置到非EEPROM地址 IAP_TRIG=0;//清除触发寄存器 } }
//菜单激活1,OUT if(SW_M==1) { if(SW_SUB_T==10&PID_OUT>0)//防抖10毫秒后操作1次 PID_OUT--;//自减1 if(SW_SUB_T==200&PID_OUT>0)//连续输入200毫秒后每50毫秒操作1次 { PID_OUT--;//自减1 SW_SUB_T=150;//计数器置数 } if(SW_ADD_T==10)//防抖10毫秒后操作1次 PID_OUT++;//自加1 if(SW_ADD_T==200)//连续输入200毫秒后每50毫秒操作1次 { PID_OUT++;//自加1 SW_ADD_T=150;//计数器置数 } //限制 if(PID_OUT>1000) PID_OUT=1000; } //菜单激活2,SV if(SW_M==2) { if(SW_SUB_T==10&PID_SV>0)//防抖10毫秒后操作1次 PID_SV--;//自减1 if(SW_SUB_T==200&PID_SV>0)//连续输入200毫秒后每50毫秒操作1次 { PID_SV--;//自减1 SW_SUB_T=150;//计数器置数 } if(SW_ADD_T==10)//防抖10毫秒后操作1次 PID_SV++;//自加1 if(SW_ADD_T==200)//连续输入200毫秒后每50毫秒操作1次 { PID_SV++;//自加1 SW_ADD_T=150;//计数器置数 } //限制 if(PID_SV>110) PID_SV=110; } //菜单激活3,MA if(SW_M==3) { if(SW_SUB_T==10)//防抖10毫秒后操作1次 PID_MA=0;//手动 if(SW_ADD_T==10)//防抖10毫秒后操作1次 PID_MA=1;//自动 if(PID_MA>1) PID_MA=1; } //菜单激活4,P if(SW_M==4) { if(SW_SUB_T==10&PID_P>0)//防抖10毫秒后操作1次 PID_P--;//自减1 if(SW_SUB_T==200&PID_P>0)//连续输入200毫秒后每50毫秒操作1次 { PID_P--;//自减1 SW_SUB_T=150;//计数器置数 } if(SW_ADD_T==10)//防抖10毫秒后操作1次 PID_P++;//自加1 if(SW_ADD_T==200)//连续输入200毫秒后每50毫秒操作1次 { PID_P++;//自加1 SW_ADD_T=150;//计数器置数 } //限制 if(PID_P>200) PID_P=200; } //菜单激活5,I if(SW_M==5) { if(SW_SUB_T==10&PID_I>0)//防抖10毫秒后操作1次 PID_I--;//自减1 if(SW_SUB_T==200&PID_I>0)//连续输入200毫秒后每50毫秒操作1次 { PID_I--;//自减1 SW_SUB_T=150;//计数器置数 } if(SW_ADD_T==10)//防抖10毫秒后操作1次 PID_I++;//自加1 if(SW_ADD_T==200)//连续输入200毫秒后每50毫秒操作1次 { PID_I++;//自加1 SW_ADD_T=150;//计数器置数 } //限制 if(PID_I>200) PID_I=200; } }
//PID_03控制-------------------------------------------------------------- void PID_03()//按键 { //PID计算 //自动模式且T_1S=0 if(PID_MA>0&T_1S==0)//自动时且1秒计时开始时 { if(PID_PV<PID_SV)//温度低 { PID_V=PID_SV-PID_PV;//计算温差 if(PID_V>3)//温度低超过3度 PID_OUT=PID_P*(PID_SV-PID_PV*9/10);//比例输出 else//温度低不超过3度 { if(PID_I_T==0)//每5秒计算1次积分 PID_OUT+=PID_I;//输出减少 } //温度差越小调节时间越长 PID_I_T++; PID_V=10-PID_V; if(PID_I_T>=PID_V)//循环计时 PID_I_T=0; }
if(PID_PV>PID_SV)//温度高 { PID_V=PID_PV-PID_SV;//计算温差 if(PID_V>5)//温度低超过5度 PID_OUT-=PID_I;//输出减少 else//温度低不超过3度 { if(PID_I_T==0) PID_OUT-=PID_I;//输出减少 } //温度差越小调节时间越长 PID_I_T++; PID_V=10-PID_V; if(PID_I_T>=PID_V)//循环计时 PID_I_T=0; } //积分计时器复位 if(PID_PV==PID_SV)//温度相等 PID_I_T=0;//积分计时器复位 } //PWM输出 //输出限制 if(PID_OUT>1000)//输出最大1000(显示100.0) PID_OUT=1000; if(PID_OUT<0)//输出最小0(显示000.0) PID_OUT=0; if(PID_PV>105|PID_PV==0)//温度超过105度或温度测量0度(0度一般是NTC电阻开路)时输出为0 PID_OUT=0; //PWM输出处理 if(T_1S>=PID_OUT)//转1秒周期的PWM输出 PWM_OUT=1;//截止 else PWM_OUT=0;//导通 }
//LCD_04显示-------------------------------------------------------------- void LCD_04()//显示 { //设置指令/数据 if(LCD_C==0|LCD_C==17)//发送缓冲区0和17时是指令,其他是数据 LCD_RS=0;//指令 else LCD_RS=1;//数据 //计数器=0时 if(LCD_C==0) { //更新缓冲区 //更新PV LCD_BUF[4]=LCD_CHAR[PID_PV/100%10];//百位字符 LCD_BUF[5]=LCD_CHAR[PID_PV/10%10];//十位字符 LCD_BUF[6]=LCD_CHAR[PID_PV%10];//个位字符 if(PID_PV<100)//小于100时百位不显示字符 LCD_BUF[4]=LCD_CHAR[10];//消影 if(PID_PV<10)//小于10时十位不显示字符 LCD_BUF[5]=LCD_CHAR[10];//消影 //更新OUT LCD_BUF[12]=LCD_CHAR[PID_OUT/1000%10];//百位字符 LCD_BUF[13]=LCD_CHAR[PID_OUT/100%10];//十位字符 LCD_BUF[14]=LCD_CHAR[PID_OUT/10%10];//个位字符 LCD_BUF[16]=LCD_CHAR[PID_OUT%10];//小数点后1位字符 if(PID_OUT<1000)//小于100.0时百位不显示字符 LCD_BUF[12]=LCD_CHAR[10];//消影 if(PID_OUT<100)//小于10.0时十位不显示字符 LCD_BUF[13]=LCD_CHAR[10];//消影 //更新SV LCD_BUF[21]=LCD_CHAR[PID_SV/100%10];//百位字符 LCD_BUF[22]=LCD_CHAR[PID_SV/10%10];//十位字符 LCD_BUF[23]=LCD_CHAR[PID_SV%10];//个位字符 if(PID_SV<100)//小于100时百位不显示字符 LCD_BUF[21]=LCD_CHAR[10];//消影 if(PID_SV<10)//小于10时十位不显示字符 LCD_BUF[22]=LCD_CHAR[10];//消影 //更新MA if(PID_MA>0)//设置为自动时 LCD_BUF[25]=LCD_CHAR[12];//显示A自动 else LCD_BUF[25]=LCD_CHAR[11];//显示M手动 //更新P,I,D if(SW_M<4)//未选择P,I,D { LCD_BUF[28]=LCD_CHAR[10];//消影 LCD_BUF[29]=LCD_CHAR[10];//消影 LCD_BUF[30]=LCD_CHAR[10];//消影 LCD_BUF[31]=LCD_CHAR[10];//消影 LCD_BUF[32]=LCD_CHAR[10];//消影 LCD_BUF[33]=LCD_CHAR[10];//消影 } if(SW_M==4)//选择P { LCD_BUF[28]=LCD_CHAR[14];//显示P LCD_BUF[29]=LCD_CHAR[16];//显示: LCD_BUF[32]=LCD_CHAR[17];//显示. LCD_BUF[30]=LCD_CHAR[PID_P/100%10];//十位字符 LCD_BUF[31]=LCD_CHAR[PID_P/10%10];//个位字符 LCD_BUF[33]=LCD_CHAR[PID_P%10];//小数点后1位字符 if(PID_P<100)//小于10.0时十位不显示字符 LCD_BUF[30]=LCD_CHAR[10];//消影 } if(SW_M==5)//选择I { LCD_BUF[28]=LCD_CHAR[15];//显示I LCD_BUF[29]=LCD_CHAR[16];//显示: LCD_BUF[32]=LCD_CHAR[17];//显示. LCD_BUF[30]=LCD_CHAR[PID_I/100%10];//十位字符 LCD_BUF[31]=LCD_CHAR[PID_I/10%10];//个位字符 LCD_BUF[33]=LCD_CHAR[PID_I%10];//小数点后1位字符 if(PID_I<100)//小于10.0时十位不显示字符 LCD_BUF[30]=LCD_CHAR[10];//消影 }
//标记消影 if(T_1S>=500)//1秒为周期,0.5秒消影,0.5秒显示 LCD_BUF[26]=LCD_CHAR[10];//消影 else LCD_BUF[26]=LCD_CHAR[13];//显示* //菜单激活消影 if(SW_SUB_T<10&SW_ADD_T<10)//按键无输入 { LCD_ON++;//消影计数 if(LCD_ON>=10)//10个输出为循环周期 LCD_ON=0;//复位 if(LCD_ON<5)//消影时间 { if(SW_M==1)//选择OUT LCD_BUF[16]=LCD_CHAR[10];//消影 if(SW_M==2)//选择SV LCD_BUF[23]=LCD_CHAR[10];//消影 if(SW_M==3)//选择MA LCD_BUF[25]=LCD_CHAR[10];//消影 if(SW_M>3)//选择P,I,D LCD_BUF[33]=LCD_CHAR[10];//消影 } } else//按键有输入 LCD_ON=0;//复位 } //输出缓冲区 LCD_DATA=LCD_BUF[LCD_C];//根据计数器输出对应的缓冲区指令或数据 LCD_E=1;//使能准备 LCD_E=0;//执行指令或数据 //计数器循环 LCD_C++;//每发送1个缓冲区计数器加1 if(LCD_C>=34)//发送完毕缓冲区复位计数器,循环发送 LCD_C=0;//复位计数器 }
//END。END。END。END。END。END。END。END。END。END。END。END。
|