用LCD1602显示
/*--------------------------------------------------------------*/
//简单频率计
//单片机: STC89C52RC
//时钟模式: 6T/双倍数
//晶振: 24MHz
//最高频率: 1.9MHz
//最大误差: 1Hz
//由于误差成线性,所以采用软件处理提高精度
//采用74HC393分频后,可以测量最高频率40MHz左右,最大误差为32Hz
//数据选择用74HC151
/*--------------------------------------------------------------*/
#include <at89x52.h>
#include "LCD1602_8A.H"
sbit Key = P1^3; //按键
sfr sel = 0x80;
/*--------------------------------------------------------------*/
unsigned char dat[8]; //显示数据
unsigned char i, counter; //循环变量和计数变量
unsigned int num; //定时变量
unsigned long x, y; //计算频率变量
unsigned char k_val; //按键变量
/*--------------------------------------------------------------*/
//变量初始化
void counter_data_init(void)
{
counter = 0;
num = 0;
for(i = 0; i < 8; i++) dat = 0;
i = 0;
}
/*--------------------------------------------------------------*/
//延时1.25s 函数定义
void delay1_25s(void)
{
unsigned char i, j, k;
for(i = 189; i > 0; i--)
for(j = 68; j > 0; j--)
for(k = 193; k > 0; k--);
}
/*--------------------------------------------------------------*/
//延时5ms 函数定义
void delay5ms(void)
{
unsigned char i, j;
for(i = 215; i > 0; i--)
for(j = 45; j > 0; j--);
}
/*--------------------------------------------------------------*/
//按键处理
void key_pro(void)
{
if(Key == 0)
{
delay5ms();
if(Key == 0)
{
k_val++;
if(k_val > 5) k_val = 0;
LCD_printc(15, 1, k_val+48);
}
while(Key == 0);
}
sel = k_val;
}
/*--------------------------------------------------------------*/
//计数定时器初始化
void ct_mode_init(void)
{
TMOD = 0x25; // T0计数,T1定时
TH0 = 0x00; TL0 = 0x00;
TH1 = 0x06; TL1 = 0x06;
ET0 = 1; ET1 = 1;
EA = 1;
TR0 = 1; TR1 = 1;
}
/*--------------------------------------------------------------*/
//主函数
void main(void)
{
LCD_init();
LCD_prints(2, 0, "System is");
LCD_prints(0, 1, "Initializing...");
delay1_25s();
LCD_clr();
LCD_prints(0, 0, "T:");
LCD_prints(12, 0, "ns");
LCD_prints(0, 1, "F:");
LCD_prints(12, 1, "Hz");
while(1)
{
counter_data_init();
ct_mode_init();
delay1_25s(); //延时1.25s,等待计数结束
x = ((unsigned long)(counter) << 16) + TH0 * 256 + TL0; //计算频率f
x <<= k_val;
y = x; //保存频率f
while(x / 10) //频率f拆位
{
dat = x % 10;
x /= 10;
i++;
}
dat = x;
LCD_printd(4, 1, dat, 8); //显示频率f
counter_data_init(); //数据初始化
if(y == 0);
else y = 1000000000 / y; //计算周期T
while(y / 10) //频率T拆位
{
dat = y % 10;
y /= 10;
i++;
}
dat = y;
LCD_printd(4, 0, dat, 8); //显示周期T
key_pro();
}
}
/*--------------------------------------------------------------*/
//计数器T0中断服务程序
void T0_counter(void) interrupt 1 using 1
{
counter++;
}
/*--------------------------------------------------------------*/
//定时器T1中断服务程序
void T1_timer(void) interrupt 3 using 3
{
num++;
if(num == 15598) {TH1 = 0x05;} //软件处理
if(num == 16000) {TR0 = 0; TR1 = 0;}
}
用户306004 2011-1-31 11:29
用户149863 2009-5-9 09:16
用户194190 2009-5-6 16:53
tengjingshu_112148725 2009-4-9 17:42