STC12C5A60S2
时间:10-02
整理:3721RD
点击:
用STC12C5A60S2进行AD采样(10位)5.0V供电,结果跳动很大,有0.05V,
和实际结果相差0.15V,怎么会这样,
以前从51一路学过来,觉得国产单片机不会太差,
所以就打算学一学STC12的AD转换部分,
结果很失望。
附上部分程序:
void ADInit()
{
// P1=0xff;
P1M1 = 0xff;
P1M0 = 0xff;
P1ASF=0xff; //P1.0口作为模拟功能AD使用
ADC_RES=0; //清零转换结果寄存器高8位
ADC_RESL=0; //清零转换结果寄存器低2位
ADC_CONTR=0xe0;//开启AD电源
Delay1ms(); //等待1ms,让AD电源稳定
write_com(0xc0);
display(str2);
}
uint getAD()
{
ADC_CONTR=0xe8;
_nop_();
_nop_();
_nop_();
_nop_();//要经过4个CPU时钟的延时,其值才能够保证被设置进ADC_CONTR 寄存器
while(!(ADC_CONTR&0x10)); //等待转换完成
ADC_CONTR=0xe0; //关闭AD转换,ADC_FLAG位由软件清0
return(ADC_RES*4+ADC_RESL); //返回AD转换完成的10位数据(16进制)
}
uint getREF()
{
ADC_CONTR=0xe9;
while(!(ADC_CONTR&0x10)); //等待转换完成
ADC_CONTR=0xe0; //关闭AD转换,ADC_FLAG位由软件清0
_nop_();
_nop_();
_nop_();
_nop_();
return(ADC_RES*4+ADC_RESL); //返回AD转换完成的10位数据(16进制)
}
void filter()
{
uchar i,j;
double k;
for(i=0;i<N;i++)
{
for(j=i;j<N;j++)
{
if(filter_data<filter_data[j])
{
k=filter_data;
filter_data=filter_data[j];
filter_data[j]=k;
}
}
}
}
void voltagedisp()
{
uchar i;
double vol=0;
for(i=0;i<N;i++)
{
CURRENT_AD=getAD();
CURRENT_REF=getREF();
}
for(i=0;i<N;i++)
{
filter_data=1.0*CURRENT_AD/CURRENT_REF;
}
filter();
for(i=N/2-5;i<N/2+5;i++)
{
vol+=3.3*filter_data; //参考电压3.3V
}
disdatavol[0]=(uint)vol/10+0x30;//个位
disdatavol[1]=(uint)vol%10+0x30;//十分位
disdatavol[2]=(uint)(vol*10)%10+0x30;//百分位
disdatavol[3]=(uint)(vol*100)%10+0x30;//千分位
write_com(0xc9);
write_dat(disdatavol[0]);
write_com(0xca);
write_dat(0x2e); //显示小数点
write_com(0xcb);
write_dat(disdatavol[1]);
write_com(0xcc);
write_dat(disdatavol[2]);
write_com(0xcd);
write_dat(disdatavol[3]);
write_com(0xce);
write_dat('V');
}
///*
void Delay1000ms() //@11.0592MHz
{
unsigned char i, j, k;
i = 43;
j = 6;
k = 203;
do
{
do
{
while (--k);
} while (--j);
} while (--i);
}
//*/
/********************主程序***********************************/
void main()
{
init_display();//初始化显示
ADInit();
while(1)
{
voltagedisp();
Delay1000ms();
}
}
- #include<stc12c5a60s2.h>
- #include "intrins.h"
- #define FOSC 11059200L
- #define BAUD 4800
- typedef unsigned char uchar;//0~255
- typedef unsigned int uint;//0~65535
- typedef unsigned long ulong;//0~4294967295
- #define ADC_START 0x08 //ADC start control bit
- #define ADC_SPEEDLL 0x00 //540 clocks
- #define ADC_SPEEDL 0x20 //360 clocks
- #define ADC_SPEEDH 0x40 //180 clocks
- #define ADC_SPEEDHH 0x60 //90 clocks
- void InitUart();
- void SendData(uchar dat);
- void Delay(uint n);
- void InitADC();
- uchar ch = 0; //ADC channel NO.
- uint Voltage,Vol;
- uchar i;
- uchar TxBuf[4]={0};
- void main()
- {
- InitUart(); //Init UART, use to show ADC result
- InitADC(); //Init ADC sfr
- IE = 0xa0; //Enable ADC interrupt and Open master interrupt switch
- //Start A/D conversion
- while (1);
- }
- /*----------------------------
- ADC interrupt service routine
- ----------------------------*/
- void adc_isr() interrupt 5 using 1
- {
- ADC_CONTR &= !ADC_FLAG; //Clear ADC interrupt flag
- Vol = ADC_RES*256+ADC_RESL;
- Voltage = Vol*500.00/1024;
- TxBuf[0]=Voltage/100+'0';
- TxBuf[1]='.';
- TxBuf[2]=Voltage%100/10+'0';
- TxBuf[3]=Voltage%10+'0';
- for(i=0;i<4;i++)
- {
- SendData(TxBuf[i]);
- }
- //if (++ch > 2) ch = 0; //switch to next channel这里只使用第0通道
- ADC_CONTR = ADC_POWER | ADC_SPEEDLL | ADC_START | ch;
- }
- /*----------------------------
- Initial ADC sfr
- ----------------------------*/
- void InitADC()
- {
- P1ASF = 0xf8; //Set all P1 as analog input port
- ADC_RES = 0; //Clear previous result
- ADC_RESL = 0;
- AUXR1 &= 0xfb; //10位
- AUXR1 |= 0x04;
- ADC_CONTR = ADC_POWER | ADC_SPEEDLL | ADC_START | ch;
- Delay(2); //ADC power-on delay and Start A/D conversion
- }
- /*----------------------------
- Initial UART
- ----------------------------*/
- void InitUart()
- {
- SCON = 0x5a; //8 bit data ,no parity bit
- TMOD = 0x20; //T1 as 8-bit auto reload
- TH1 = TL1 = -(FOSC/12/32/BAUD); //Set Uart baudrate
- TR1 = 1; //T1 start running
- }
- /*----------------------------
- Send one byte data to PC
- Input: dat (UART data)
- Output:-
- ----------------------------*/
- void SendData(uchar dat)
- {
- while (!TI); //Wait for the previous data is sent£?TIê?′?DD?ú1·¢?í?D??±ê??
- TI = 0; //Clear TI flag
- SBUF = dat; //Send current data
- }
- /*----------------------------
- Software delay function
- ----------------------------*/
- void Delay(uint n)
- {
- uint x;
- while (n--)
- {
- x = 5000;
- while (x--);
- }
- }

正常,很多时候需要处理的。更有人在前面加跟随器!
shiyigehaotie!
好厉害,学习了
学习 学习
