微波EDA网,见证研发工程师的成长!
首页 > 研发问答 > 嵌入式设计讨论 > MCU和单片机设计讨论 > 12864显示ad采集压力值怎么压传感器都不变,估计是程序问题,自己怎么查也查不出错

12864显示ad采集压力值怎么压传感器都不变,估计是程序问题,自己怎么查也查不出错

时间:10-02 整理:3721RD 点击:
#include <reg52.h>
#include <intrins.h>
#include <stdio.h>
#define MAIN_Fosc                11059200UL        //宏定义主时钟HZ
#define PCF8591_ADDR        0x90                //PCF8591地址

/*====================================
自定义类型名
====================================*/
typedef unsigned char INT8U;
typedef unsigned char uchar;
typedef unsigned int INT16U;
typedef unsigned int uint;
/*====================================
硬件接口位声明
====================================*/
sbit SDA = P2^0;   //I2C串行数据
sbit SCL = P2^1;   //I2C串行时钟
sbit DU  = P2^6;   //数码管段选
sbit WE  = P2^7;   //数码管位选
sbit EN = P3^4;        // 液晶使能控制
sbit RS = P3^5;         //数据命令选择端
sbit RW = P3^6;         //读写选择端
sbit LCD_PSB = P3^7;//串行选择端
uint AD_Value;        //存储AD转换回的数字量
uchar i,temp,com;
uchar code dis1[]={"压力值:"};
uchar code dis2[]={"角度值:"};
/*====================================
函数:void Delay_Ms(INT16U ms)
参数:ms,毫秒延时形参
描述:12T 51单片机自适应主时钟毫秒级延时函数
====================================*/
void Delay_Ms(INT16U ms)
{
     INT16U i;
         do{
              i = MAIN_Fosc / 96000;
                  while(--i);   //96T per loop
     }while(--ms);
}
/*====================================
函数:void Delay5us()
描述:12T 51单片机5微秒延时函数自适应时钟(11.0592M,12M,22.1184M)
====================================*/
void Delay5us()
{
        #if MAIN_Fosc == 11059200
                _nop_();
        #elif MAIN_Fosc == 12000000
                _nop_()
        #elif MAIN_Fosc == 22118400
                _nop_(); _nop_(); _nop_();
        #endif
}

/*====================================
函数:I2C_init()
描述:I2C总线初始化
====================================*/
void I2C_init()
{
        SDA = 1;   //数据总线高
        _nop_();
        SCL = 1;   //时钟总线高
        _nop_();
}
/*====================================
函数:I2C_Start()
描述:I2C起始信号
====================================*/
void I2C_Start()  
{
        SCL = 1;
        _nop_();
        SDA = 1;
        Delay5us();
        SDA = 0;
        Delay5us();
}
/*====================================
函数:I2C_Stop()
描述:I2C停止信号
====================================*/
void I2C_Stop()
{
        SDA = 0;
        _nop_();
        SCL = 1;
        Delay5us();
        SDA = 1;
        Delay5us();
}
/*====================================
函数:Master_ACK(bit i)
参数:i 为0时发送非应答 为1时发送应答
描述:I2C主机发送应答
====================================*/
void Master_ACK(bit i)        
{
        SCL = 0; // 拉低时钟总线允许SDA数据总线上的数据变化
        _nop_(); // 让总线稳定
        if (i)         //如果i = 1 那么拉低数据总线 表示主机应答
        {
                SDA = 0;
        }
        else         
        {
                SDA = 1;         //发送非应答
        }
        _nop_();//让总线稳定
        SCL = 1;//拉高时钟总线 让从机从SDA线上读走 主机的应答信号
        _nop_();
        SCL = 0;//拉低时钟总线, 占用总线继续通信
        _nop_();
        SDA = 1;//释放SDA数据总线。
        _nop_();
}
/*====================================
函数:Test_ACK()
返回:0为非应答 1为应答
描述:I2C检测从机应答
====================================*/
bit Test_ACK()         // 检测从机应答
{
        SCL = 1;//时钟总线为高电平期间可以读取从机应答信号
        Delay5us();
        if (SDA)
        {
                SCL = 0;
                I2C_Stop();
                return(0);
        }
        else
        {
                SCL = 0;
                return(1);
        }
}
/*====================================
函数:I2C_send_byte(uchar byte)
参数:byte 要发送的字节
描述:I2C发送一个字节
====================================*/
void I2C_send_byte(uchar byte)
{
        uchar i;
        for(i = 0 ; i < 8 ; i++)
        {
                SCL = 0;
                _nop_();
                if (byte & 0x80)        //
                {
                        SDA = 1;
                        _nop_();
                }
                else
                {
                        SDA = 0;
                        _nop_();
                }
                SCL = 1;
                _nop_();
                byte <<= 1;
        }
        SCL = 0;
        _nop_();
        SDA = 1;
        _nop_();        
}
/*====================================
函数:I2C_read_byte()
返回:读取的字节
描述:I2C读一个字节
====================================*/
uchar I2C_read_byte()
{
        uchar i, dat;
        SCL = 0 ;
        _nop_();
        SDA = 1;
        _nop_();
        for(i = 0 ; i < 8 ; i++)
        {
                SCL = 1;
                _nop_();
                dat <<= 1;         
                if (SDA)
                {
                        dat |= 0x01;  
                }
                _nop_();
                SCL = 0;
                _nop_();
        }
        return(dat);
}
/*读AD数据*/
bit ADC_Read(uchar CON)
{
        I2C_Start();
        I2C_send_byte(PCF8591_ADDR+0);
        if (!Test_ACK())
        {
                return(0);
        }
        I2C_send_byte(CON);
        Master_ACK(0);
        I2C_Start();
        I2C_send_byte(PCF8591_ADDR+1);
        if (!Test_ACK())
        {
                return(0);
        }
        AD_Value = I2C_read_byte();
        Master_ACK(0);
        I2C_Stop();
        return(1);        
}

/*void delay(uint z)
{
        uint x,y;
        for(x = z; x > 0; x--)
                for(y = 114; y > 0 ; y--);
}        */
/*====================================
函数:LCD_status()
描述:判断忙
====================================*/
bit lcd_status()
{
        bit status;
        RS = 0;
        RW = 1;
         Delay_Ms(5);
    EN = 1;
        status = P0&0x80;
        EN = 0;
        return(status);
}
/*====================================
函数:write_cmd()
描述:写指令到LCD
====================================*/
void write_cmd( uchar cmd)
{
        while(lcd_status());
        RS = 0;
        RW = 0;
        EN = 0;
        P0 = cmd;
        Delay_Ms(5);
        EN= 1;
        Delay_Ms(5);
        EN = 0;               
}
/*====================================
函数:write_dat()
描述:写数据到LCD
====================================*/
void write_dat( uchar dat)
{
        while(lcd_status());
        RS = 1;
        RW = 0;
        EN = 0;
        P0 = dat;
        Delay_Ms(5);
        EN= 1;
        Delay_Ms(5);
        EN = 0;               
}
/*====================================
函数:write_dat()
描述:设定显示位置
====================================*/
void lcd_pos(uchar X,uchar Y)
{
         uchar pos;
        switch(X)
        {
                 case 0:        X = 0x80;break;
                case 1:        X = 0x90;break;
                case 2:        X = 0x88;break;
                case 3:        X = 0x98;break;
        }
        pos = X+Y;
        write_cmd(pos);
}
/*
/*====================================
函数:lcd_init()
描述:lcd初始化
====================================*/
void lcd_init()
{
         LCD_PSB = 1;
        write_cmd(0x30);
        Delay_Ms(5);
        write_cmd(0x0c);
        Delay_Ms(5);        
        write_cmd(0x01);
        Delay_Ms(5);
}
/* void ad_display(uint i)
{
        uint t1,t2,t3,t4,t5;
        if( 10000 < i <100000)
        {
                t1 = i/10000 +0x30;
                t2 = i/10000%1000+0x30 ;
                t3 = i%1000/100 +0x30;
                t4 = i%100/10 +0x30;
                t5 = i%10+0x30;
                write_dat(t1);
                write_dat(t2);
                write_dat(t3);
                write_dat('.');        
                write_dat(t4);
                write_dat(t5);
        }
        else if(1000<i<10000)
        {
                t1 =  i/1000+0x30;
                t2 =  i/1000%100+0x30;
                t3 = i%100/10 +0x30;
                t4 = i%10 +0x30;
                write_dat(t1);
                write_dat(t2);
                write_dat('.');
                write_dat(t3);
                write_dat(t4);
        }
        else if(10<i<1000)
        {
                t1 = i/100+0x30;
                t2 = i/100%10+0x30;
                t3 = i%10+0x30;
                write_dat(t1);
                write_dat('.');
                write_dat(t2);
                write_dat(t3);
        }
}
*/

void display(uint i)
{
    uchar count,tmp;
    uchar datas[] = {0, 0, 0, 0, 0,0};
    datas[0] = tmp / 10000;
    datas[1] = tmp % 10000 / 1000;
    datas[2] = tmp % 1000 / 100;
    datas[3] = tmp % 100 / 10;
    datas[4] = tmp % 10;
          lcd_pos(0,4);
    for(count = 1; count != 6; count++)
    {
        write_dat('0'+datas[count]);
        if(count == 3)
        {
            write_dat('.');
        }
    }
}
void main()
{
    uchar a,b;
        WE= 0;
        DU = 0;
        I2C_init();
        lcd_init();
        while(1)
        {        
               
                lcd_pos(0,0);
                a = 0;
                while(dis1[a]!='\0')
                {
                        write_dat(dis1[a]);
                        a++;
                }
                lcd_pos(0,7);
                write_dat('N');
                ADC_Read(0x03);
                 com        = (uint)(AD_Value*1.17*100 );
                display(com);
                lcd_pos(2,0);
                b = 0;
                while(dis2!='\0')
                {
                        write_dat(dis2);
                        b++;
                }
        }                        
}

试试看这里吧,形参是i,函数中对tmp做计算,并没有对i做计算
void display(uint i)
{
    uchar count,tmp;
    uchar datas[] = {0, 0, 0, 0, 0,0};
    datas[0] = tmp / 10000;
    datas[1] = tmp % 10000 / 1000;
    datas[2] = tmp % 1000 / 100;

刚改了,可是显示数值变乱了,初始值也不是零,一会变大一会变小,我的显示函数是不是写的有问题啊

你可以随意给定一些数值来显示,判断是否显示程序有问题,如果显示程序没问题,那就是传感器部分的问题了

建议把
for(count = 1; count != 6; count++)
    {
        write_dat('0'+datas[count]);
        if(count == 3)
        {
            write_dat('.');
        }
    }
改成
write_dat(t1);
                write_dat(t2);
                write_dat(t3);
                write_dat('.');        
                write_dat(t4);
                write_dat(t5);这种方式,不做循环,每次显示一个数值,另外做了datas[0] = tmp / 10000;,但是却不显示

刚刚又改了,随便另AD-Value取了几个值放进去,发现显示的还是不对。
void display(uint tmp)
{
   
    uint datas[6];
    datas[0] = tmp / 10000;
    datas[1] = tmp /10000%1000 ;
    datas[2] = tmp % 1000 / 100;
    datas[4] = tmp % 100 / 10;
    datas[5] = tmp % 10;
         lcd_pos(0,4);
                 write_dat('0'+datas[0]);
                write_dat('0'+datas[1]);
                write_dat('0'+datas[2]);
                write_dat('.');
                write_dat('0'+datas[4]);
                write_dat('0'+datas[5]);
   
}

Copyright © 2017-2020 微波EDA网 版权所有

网站地图

Top