1.將程序下載進去后,第一行顯示RMB/kg: (計價數據)第二行顯示m:(重量)K P:(價格)¥
2.仿真圖是利用四個電位器模擬稱重傳感器的四個電阻應變式電阻,通過調節這四個電位器的大小可以測量物體的重量,但是程序有個漏洞就是調節電位器的大小不能及時的反應物體的重量,需要按下ENTER鍵才能檢測物體的重量,此程序還待優化
3.通過按鍵可以設定物品的計價,程序中設計的每千克多少錢,程序只支持設定整數價格(小數價格朋友可以自己適當修改下即可),當設定好價格后按下ENTER鍵即可顯示物品的重量及價格,如果還要設定其他的價格,則需要按下CLEAR清除按鍵再設定即可。
4.此電子秤最大稱重為5KG,計價總和最大為999.99。
5.此設計還可以添加語音錄放模塊,實現智能化報價
6.電子秤LCD上顯示的重量值是電阻應變器電橋的對邊電壓,這樣一來我們可以利用這個電壓值反應稱重的重量
仿真原理圖如下(proteus仿真工程文件可到本帖附件中下載)
~6`D76Y4QX)3`ZQ[YZ5~940.jpg (659.43 KB, 下載次數: 129)
下載附件
2018-7-2 16:29 上傳
#include<reg52.h>
typedef unsigned char uint8;
typedef unsigned int uint16;
sbit rs=P2^6;
sbit rw=P2^5;
sbit e=P2^7;
sbit scl=P2^1;
sbit sda=P2^0;
uint8 num[]="0123456789";
uint8 d1[]="RMB/kg: ";
uint16 ad[5],m[5];
uint8 kn=10;
uint8 keynum[3];
uint16 pric=0;
void delay(uint16 i)
{
while(i--);
}
void wrc(uint8 c)
{
delay(1000);
rs=0;
rw=0;
e=0;
P0=c;
e=1;
delay(10);
e=0;
}
void wrd(uint8 dat)
{
delay(1000);
rs=1;
rw=0;
e=0;
P0=dat;
e=1;
delay(10);
e=0;
rs=0;
}
void init()
{
delay(1000);
wrc(0x38);
wrc(0x38);
wrc(0x38);
wrc(0x06);
wrc(0x0c);
wrc(0x01);
}
void iicinit()
{
sda=1;
scl=1;
}
void iicstart()
{
sda=1;
scl=1;
delay(10);
sda=0;
delay(10);
scl=0;
delay(10);
}
void iicstop()
{
sda=0;
scl=1;
delay(10);
sda=1;
delay(10);
sda=0;
delay(10);
}
void ack()
{
sda=1;
scl=0;
delay(2);
sda=0;
delay(2);
scl=1;
delay(10);
scl=0;
delay(2);
sda=1;
delay(5);
}
void noack()
{
sda=0;
scl=0;
delay(2);
sda=1;
delay(2);
scl=1;
delay(10);
scl=0;
delay(2);
sda=0;
delay(5);
}
void iicwrbyte(uint8 dat)
{
uint8 i;
scl=0;
for(i=0;i<8;i++)
{
if(dat&0x80)
{
sda=1;
}
else
{
sda=0;
}
dat<<=1;
scl=1;
delay(10);
scl=0;
delay(10);
}
sda=1;
delay(10);
}
uint8 iicread()
{
uint8 i,dat;
scl=0;
sda=1;
for(i=0;i<8;i++)
{
dat<<=1;
if(sda==1)
{
dat|=0x01;
}
scl=1;
delay(10);
scl=0;
delay(10);
}
return dat;
}
void pcf8591wrbyte(uint8 channel)
{
iicinit();
iicstart();
iicwrbyte(0x90); //pcf8591寫數據 1001 A2A1A0 R/W
ack();
iicwrbyte(channel|0x70); //通過打開通道channelX,模擬輸出使能打開
noack();
iicstop();
}
uint8 pcf8591read()
{
uint8 dat;
iicinit();
iicstart();
iicwrbyte(0x90);
ack();
iicstart();
iicwrbyte(0x91); // pcf8591讀數據 1001 A2A1A0 R/W
ack();
dat=iicread();
noack();
iicstop();
return dat;
}
void pcf8591dac(uint8 value) //DA轉換
{
iicinit();
iicstart();
iicwrbyte(0x90);
ack();
iicwrbyte(0x70); //不需要打開通道channelX,模擬輸出使能打開
ack();
iicwrbyte(value);
noack();
iicstop();
}
uint8 keyscan() //按鍵掃描程序
{
uint8 h,l,value;
P1=0x0f;
h=P1&0x0f;
if(h!=0x0f)
{
delay(1);
if(h!=0x0f)
{
h=P1&0x0f;
l=P1|0xf0;
P1=l;
l=P1&0xf0;
h=P1&0x0f;
value=h+l;
}
return value;
}
}
void keypros() //按鍵處理函數
{
uint8 key;
key=keyscan();
switch(key)
{
case 0xee: kn=0;break;
case 0xde: kn=1;break;
case 0xbe: kn=2;break;
case 0x7e: kn=3;break;
case 0xed: kn=4;break;
case 0xdd: kn=5;break;
case 0xbd: kn=6;break;
case 0x7d: kn=7;break;
case 0xeb: kn=8;break;
case 0xdb: kn=9;break;
case 0xbb: break;
case 0x7b: break;
case 0xe7: kn=12;break; //小數點按下標志位
case 0xd7: kn=11;break; //計價確認按鍵標志
case 0xb7: kn=13;break; //clear,清空計價輸入
case 0x77: break;
default : break;
}
}
void datapros()
{
uint8 i,count=0;
do //將按鍵值保存在數組keynum中
{
P1=0x0f;
if(P1!=0x0f)
{
keypros();
P1=0x0f;
while(P1!=0x0f);//等待按鍵松開
if(kn>=0&&kn<=9)
{
keynum[count]=kn;
wrc(0x0b+count+0x80); //移位顯示
wrd(keynum[count]+0x30);
count++;
}
if(kn==13) //清除按鍵計價數
{
wrc(0x01);//清屏處理
pric=0;
}
if(kn==11) //當計價確認按鍵按下時候退出循環
{
goto xian;
}
}
}
while(count<=2);
if(count>=2)
{
goto xian;
}
xian: for(i=0;i<count;i++)
{
pric=pric*10+keynum[ i];
if(i==count)count=0;//當進行一次轉換后清空計數器的值
}
}
void display()
{
float v;
uint8 i;
uint16 price;
pcf8591wrbyte(0); //電位器轉換
ad[0]=pcf8591read(); //讀取第一次之前的那次數據
delay(10);
v=ad[0]*0.01953;//將電位器的數據轉換成電壓值
v=v*100;//取2位有效數值
ad[0]=v;
price=ad[0]*pric; //每千克多少錢如果我們定義每千克2元那么就可以乘以2,如果為其他我們可以乘以其他數,最大定義的價格是200元每千克
wrc(0x00+0x80);
for(i=0;i<8;i++)
{
wrd(d1[i ]);
}
wrc(0x40+0x80);
wrd('m');
wrd(':');
wrd(num[ad[0]/100]);
wrd('.');
wrd(num[ad[0]%100/10]);
wrd(num[ad[0]%100%10]);
// wrd(num[ad[0]%1000%100%10]);
wrd('K');
// wrd('G');
ad[4]=ad[0];
pcf8591dac(ad[4]/2);//將數字量轉換為模擬量由pcf8591的AOUT輸出
wrd(' ');
wrd('P');
wrd(':');
wrd(num[price/10000]);//為什么是除以10000,本來不計價的話是除以100,但是計價最大可以使百位數,所以除以的數也得乘以100
wrd(num[price%10000/1000]);
wrd(num[price%10000%1000/100]);
wrd('.');
if((price%10000%1000%100%10)>=5) //進價,四舍五入法
wrd(num[(price%10000%1000%100/10)+1]);
else
wrd(num[price%10000%1000%100/10]);
wrd('$');
}
void main()
{
init();
while(1)
{
display();
datapros();
}
}
0.png (53.45 KB, 下載次數: 81)
下載附件
2018-7-3 02:17 上傳
全部資料51hei下載地址:
基于單片機設計的數字電子秤(程序,proteus仿真,原理圖都有).zip
(2.93 MB, 下載次數: 762)
2018-7-2 16:29 上傳
點擊文件名下載附件
下載積分: 黑幣 -5
|