標題:
單片機1602電壓電流表原理圖和源程序
[打印本頁]
作者:
無名氏1957
時間:
2022-1-3 13:13
標題:
單片機1602電壓電流表原理圖和源程序
1602電壓電流表制作.png
(6.62 KB, 下載次數: 93)
下載附件
2022-1-3 17:58 上傳
單片機源程序如下:
/******引腳說明LCD液晶RS2.5 RW2.6 E2.7 DB0~DB7:P0.0~P0.7
電壓測量P1.1;需要0~30v需要加分流電阻,,分辨率0.03v;
電流側量P1.7;需要加放大電路如lm358;op07等,分辨率3ma
**********/
//stc12c5a60
#include<STC12C5A60S2.h>
#include<stdio.h>
#include<intrins.h>//頭文件
#define uchar unsigned char//宏定義
#define uint unsigned int//宏定義
#define ulint unsigned long int//宏定義
#define N 21//ADC中值濾波次數,必須為基數
#define ISP_TRIG() ISP_TRIG=0x5A,ISP_TRIG=0xA5//ISP觸發(fā)命令
sbit rs=P3^5;//液晶RS
sbit rw=P3^6;//液晶RW
sbit e=P3^4;//液晶E
void AD_init(void);//ADC初始化
void delay(uint z);//延時函數
uint AD_get(uchar haha );//讀ADC的數值
void LCD_data(uchar shuju);//寫數據
void zhiling(uchar zhilin);//寫指令
void LCD_init(void);//初始化LCD
void tablex(uint tab);//數據分解
uint filter(uchar dat);//中值濾波
void timer_init(void);//定時器初始化
uchar h1,h2,h3,h4;//LCD顯示變量
ulint mas,maz;//容量計算
uchar table[]="0123456789";//顯示數組
uchar table1[]=".VAWa";
void main()
{
ulint tempv,tempa;//存放電壓電流值
AD_init();//ADC初始化
timer_init();//定時器初始化
LCD_init();//LCD初始化
while(1)
{
tempv=filter(0x88);//設置ADC通道0、開始轉換
tablex(tempv*3);//分解數據
zhiling(0x80);//LCD地址
LCD_data(table[h1]);//
LCD_data(table[h2]);//
LCD_data(table1[0]);//
LCD_data(table[h3]);//
LCD_data(table[h4]);//
LCD_data(table1[1]);//顯示
tempa=filter(0x8f);//設置ADC通道7、開始轉換
if(tempa<=10)//防止數據成負數
tempa=10;
mas=tempa*3-30;//計算容量取樣賦值
tablex(tempa*3-30);//減去LM358失調的數值
zhiling(0x88);//LCD地址
LCD_data(table[h1]);
LCD_data(table1[0]);
LCD_data(table[h2]);
LCD_data(table[h3]);
LCD_data(table[h4]);
LCD_data(table1[2]);
tablex((tempv*3/10)*((tempa*3-30)/10)/10);//計算功率
zhiling(0x80+0x40);
LCD_data(table[h1]);
LCD_data(table[h2]);
LCD_data(table1[0]);
LCD_data(table[h3]);
LCD_data(table[h4]);
LCD_data(table1[3]);
tablex(maz/1000);//顯示MAH
zhiling(0x88+0x40);
LCD_data(table[h1]);
LCD_data(table1[0]);
LCD_data(table[h2]);
LCD_data(table[h3]);
LCD_data(table[h4]);
LCD_data(table1[4]);
}
}
//-------------------------------------------------------------
void delay(uint z)///////////////延時程序
{
uint x,y;
for(x=z;x>0;x--)
for(y=19;y>0;y--);
}
void AD_init(void)/////////////////////初始化ADC
{
P1ASF=0xff;//P1口全部作為模擬功能AD使用
ADC_RES=0;//清零轉換結果寄存器高8位
ADC_RESL=0;//清零轉換結果寄存器低2位
ADC_CONTR=0x80;//開啟AD電源
delay(5);//等待1ms,讓AD電源穩(wěn)定
}
uint AD_get(uchar haha )//ADC讀數
{
uint rew;
ADC_CONTR=haha;//開啟AD轉換
_nop_(); _nop_(); _nop_(); _nop_();//要經過4個CPU時鐘的延時
while(!(ADC_CONTR&0x10));//等待轉換完成
ADC_CONTR&=0xe7;//關閉AD轉換,ADC_FLAG位由軟件清0
rew=ADC_RES*4+ADC_RESL;//組合成10位
delay(1);//等待
return rew;//返回ADC值
}
void zhiling(uchar zhilin)//寫指令
{
e=0;
rs=0;
rw=0;
P0=zhilin;
delay(20);
e=1;
delay(20);
e=0;
}
void LCD_data(uchar shuju)//寫數據
{
e=0;
rs=1;
rw=0;
P0=shuju;
delay(20);
e=1;
delay(20);
e=0;
}
void LCD_init(void)//初始化LCD
{
delay(300);
zhiling(0x38);
delay(100);
zhiling(0x38);
delay(100);
zhiling(0x38);
delay(100);
zhiling(0x38);
zhiling(0x38);
zhiling(0x08);
zhiling(0x01);
zhiling(0x06);
zhiling(0x0c);
}
void tablex(uint tab1)//數據分解
{
h1=tab1/1000;//1023//1
h2=tab1%1000/100;//023//0
h3=tab1%100/10;//23//2
h4=tab1%10;//3
}
uint filter(uchar dat)//中位值濾波
{
uint value_buf[N];
uint count,i,j,temp;
for(count=0;count<N;count++)
{
AD_init();//初始化ADC
value_buf[count] = AD_get(dat);//讀ADC數值
delay(1);
}
for (j=0;j<N-1;j++)
{
for (i=0;i<N-j;i++)
{
if ( value_buf[i]>value_buf[i+1] )
{
temp = value_buf[i];
value_buf[i] = value_buf[i+1];
value_buf[i+1] = temp;
}
}
}
return value_buf[(N-1)/2];
}
void timer_init(void)//定時器初始化
{
TMOD=0x01;/////////設置工作方式1
TH0=(65536-50000)/256;///////賦值
TL0=(65536-50000)%256;
EA=1;ET0=1;//開總中斷;開定時器中斷
TR0=1;////////啟動計數器
}
復制代碼
作者:
liuyiyi
時間:
2022-1-4 11:41
希望多這樣的作者,既不要黑B,還能學習
作者:
金越科技
時間:
2022-3-31 20:40
要下來學習 這個程序很好找了好久了——可以用——,
作者:
caihj3
時間:
2022-4-1 12:04
原理圖如能清晰一些就更好,謝謝分享。
作者:
electmo
時間:
2023-3-22 18:59
Proteus仿真沒有數字顯示怎么會事?
歡迎光臨 (http://www.torrancerestoration.com/bbs/)
Powered by Discuz! X3.1