电子装置与系统设计课程设计报告.docx
《电子装置与系统设计课程设计报告.docx》由会员分享,可在线阅读,更多相关《电子装置与系统设计课程设计报告.docx(23页珍藏版)》请在冰豆网上搜索。
![电子装置与系统设计课程设计报告.docx](https://file1.bdocx.com/fileroot1/2023-2/7/dea28d15-6869-49e2-a881-59209d3c144c/dea28d15-6869-49e2-a881-59209d3c144c1.gif)
电子装置与系统设计课程设计报告
电子装置与系统设计课程设计
学院:
信息电子学院
班级:
08电子信息工程
学号:
E08610308
姓名:
陈建能
指导老师:
陈科\沈军民
日期:
2011\07\04
1、课程设计目的………………………………………………………………3
2、课程设计工具及题目………………………………………………………3
2.1、课程设计工具…………………………………………………...……3
2.2、课程设计题目……………………………………………...…………3
3、课程设计内容、步骤及电路原理图………………………………………3
3.1、课程设计内容………………………………………………………..3
3.2、课程设计步骤………………………………………………………..3
3.3、整个系统的电路原理图……………………………………………..4
4、课程设计各模块工作原理…………………………………………………5
4.1、红外心率计模块.……………………………………………………...5
4.1.1、负电源变换电路………………………………………………5
4.1.2、血液波动检测电路……............................................................6
4.1.3、放大、整形、滤波电路…………………………………........7
4.2、PIC单片机检测并显示模块…………………………………………8
4.2.1、定时器初始化及中断函数…………………………………....8
4.2.2、数脉冲个数程序……………………………………………....9
4.2.3、数码管显示程序………...……………………………………10
4.2.4、延时子程序…….……………………………………………...11
4.2.5、ds18b20温度采集程序………………………………………..11
5、课程设计心得……………………………………………………………....14
6、参考文献…………………………………………………………………....15
7、附录:
源程序代码及注释…………………………………………………16
课程设计目的:
单片机具有体积小、功能强、成本低、应用面广等优点,可以说,智能控制与自动控制的核心就是单片机。
目前,一个学习与应用单片机的高潮在全社会大规模地兴起。
学习单片机的最有效方法就是理论与实践并重。
系统地运用已学的理论知识解决实际问题的能力和查阅资料的能力。
培养一定的自学能力和独立分析问题、解决问题的能力,能通过独立思考、查阅工具书、参考文献,寻找解决方案;
课程设计工具及题目:
1、课程设计工具:
PC机、PIC单片机最小系统、红外心率计模块
2、课程设计题目:
基于PIC单片机的脉搏检测
课程设计内容、步骤及电路原理图
1、学习PCB画图,选好课题,即脉搏检测。
购买元器件材料,焊接PIC最小系统版,搭建心率计模块,然后由心率计模块产生方波,用PIC单片机数出一分钟的脉冲个数,然后在数码管上显示出来,即为脉搏。
2、首先根据最小系统版的原理图,搭建好电路,调试下载线是否可以下载,复位开关是否可以工作。
调试成功之后,开始搭建心率计模块,搭建好心率计模块之后,开始检测是否可以产生方波,用手指按在传感器上,然后用示波器观察是否出现方波脉冲。
调试成功之后,就编写相应的程序,烧写进单片机中,然后就可以检测相应的脉搏了。
3、红外心率计模块电路图
4、PIC单片机最小系统原理图
各功能模块的工作原理:
1、红外心率计模块
单元电路的工作原理
⑴负电源变换电路
负电源变换电路的作用是把+12V直流电变成-10V左右的直流电压,-10V电压与+12V作为运算放大器的电源。
负电源变换电路如图2所示,其中IC1(CD4069)为六非门集成电路,它的内部结构图如图3(a)所示。
负电源变换电路工作原理:
通电的瞬间,假设A点是低电位,则B点是高电位,C点是低电位,D点是高电位。
B点的高电位通过R19给C7充电,当F点的电压高于IC1(CD4049)的电平转换电压时,B点输出低电位,C点(C7一端)输出高电位,由于电容两端的电压不能突变,所以C7两端的电压通过R19放电。
当F点电压低于IC1的转换电压时,B点输出高电位,此高电位通过R19对C7充电,如此循环。
C点得到方波,经过后面四个反相器反相、扩流后,在D点得到方波。
当D点是高电平的时候,V1导通C8被充电,大约充到11V左右,当D点变成低电平的时候,由于C8两端电压不能突变,G点电压被拉到-11V左右,此时V2导通,C9反方向进行充电,使E点电压达到-10V左右。
由于带负载的能力不强,当带上负载后,E点电压大约降到9V左右。
图2电源电路
(a)CD4049(b)LM741
图3集成电路的结构图
⑵血液波动检测电路
血液波动检测电路首先通过红外光电传感器把血液中波动的成分检测出来,然后通过电容器耦合到放大器的输入端。
如图4所示。
图4血液波动检测电路
TCRT5000红外光电传感器的检测方法:
首先用数字万用表的二极管档位正向压降测试控制端发射管(浅蓝色)的正、负极,将红黑表笔分别接发射管的两个引脚,正反各测一次,表头一次显示“1.05(0.9-1.1)”,一次显示溢出值“-1”,则显示1.05V的那次正确,红表笔接的是正极,黑表笔接的是负极。
若两次都显示“1”,说明发射管内部开路,若两次都显示“0”发射管内不短路。
然后再判断接收管的C、E极和光电转换效率,方法如下:
将发射管的正负极分别插入数字万用表hFE档NPN型的C、E插孔,再将模拟万用表打到R×1kΩ档。
红黑表笔分别接接收管的两个引脚,若表针不动,则红黑表笔对调,若表针向右偏转到15kΩ左右,则黑表笔所接管脚为C,红表笔所接管脚为E。
此时,再用手指或白纸贴近两管上方,表针继续向右偏转至1kΩ以内,说明该红外光电断续器的光电转换效率高。
血液波动检测电路工作原理:
TCRT5000是集红外线发射管、接收管为一体的器件,工作时把探头贴在手指上,力度要适中。
红外线发射管发出的红外线穿过动脉血管经手指指骨反射回来,反射回来的信号强度随着血液流动的变化而变化,接收管把反射回来的光信号变成微弱的电信号,并通过C1耦合到放大器。
⑶放大、整形、滤波电路
放大、整形、滤波电路是把传感起检测到的微弱电信号进行放大、整形、滤波,最后输出反映心跳频率的方波,如图5所示。
其中LM741为高精度单运放电路,它们的引脚功能如图3(b)所示。
IC2、IC3、IC4都为LM741。
图5 信号放大、整形电路
因为传感器送来的信号幅度只有2~5毫伏,要放大到10V左右才能作为计数器的输入脉冲。
因此放大倍数设计在4000倍左右。
两级放大器都接成反相比例放大器的电路,经过两级放大、反相后的波形是跟输入波形同相、且放大了的波形。
放大后的波形是一个交流信号。
其中A1、A2的供电方式是正负电源供电,电源为+12V、-10V。
A1、A2与周围元件组成二级放大电路,放大倍数Auf为:
由于放大后的波形是一个交流信号,而计数器需要的是单方向的直流脉冲信号。
所以经过V3检波后变成单方向的直流脉冲信号,并把检波后的信号送到RC两阶滤波电路,滤波电路的作用是滤除放大后的干扰信号。
R9、V4组成传感器工作指示电路,当传感器接收到心跳信号时,V4就会按心跳的强度而改变亮度,因此V4正常工作时是按心跳的频率闪烁。
直流脉冲信号滤波后送入A3的同相输入端,反相输入端接一个固定的电平,A3是作为一个电压比较器来工作的,是单电源供电。
当A3的3脚电压高于2脚电压的时候,6脚输出高电平;当A3的3脚电压低于2脚电压的时候,6脚输出低电平,所以A3输出一个反应心跳频率的方波信号。
2、PIC单片机检测并显示模块
定时器,定时1s实现60秒的计时功能,用于检测的时间,并在数码管上显示出来。
相应的初始化程序为:
voidtime1_rtc_init(void)
{
INTCON=0x20;//disableglobalandenableTMR0interrupt
INTCON2=0x84;//TMR0highpriority
RCONbits.IPEN=1;//enableprioritylevels
TMR0H=100;//cleartimer
TMR0L=0;//cleartimer
T0CON=0x85;//setuptimer0-prescaler1:
64
INTCONbits.GIEH=1;//enableinterrupts
}
定时器的中断函数为:
#pragmacodeInterruptVectorHigh=0x08
void
InterruptVectorHigh(void)
{
_asm
gotoInterruptHandlerHigh//jumptointerruptroutine
_endasm
}
#pragmacode
#pragmainterruptInterruptHandlerHigh
voidInterruptHandlerHigh()
{
if(INTCONbits.TMR0IF)
{//checkforTMR0overflow
INTCONbits.TMR0IF=0;//clearinterruptflag
second++;//indicatetimeout
if(second==60)
{
second=0;
result=1;
}
//if(result!
=1)
//led=~led;
}
}
由RB0采集脉搏的方波,计数方波个数,并在60秒后显示在数码管上。
#definepulsePORTBbits.RB0
采用上升沿触发来实现计数功能,从而实现了计数方波的个数的功能。
if(INTCONbits.INT0IF==1)
{
INTCONbits.INT0IF=0;
delay_ms(100);
fre++;
}
位选和段选的数值和数码管的显示程序如下:
constunsignedtable[10]=
{0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,0x7F,0x6F};
constunsignedbit_set[4]={0xFE,0xFD,0xFB,0xF7};
voiddisplay(inttime)
{
PORTC=table[time%10];
PORTD=bit_set[3];
delay_ms(20);
PORTC=table[(time/10)%10];
PORTD=bit_set[2];
delay_ms(20);
PORTC=table[time/100];
PORTD=bit_set[1];
delay_ms(20);
}
显示带小数位的,代码如下:
voiddisplay1(inttime)
{
PORTC=table[time%10];
PORTD=bit_set[3];
delay_ms(10);
PORTC=table1[(time/10)%10];
PORTD=bit_set[2];
delay_ms(10);
PORTC=table[(time)/100];
PORTD=bit_set[1];
delay_ms(10);
}
延时子程序如下:
voiddelay_ms(unsignedinttime)
{
intn;
for(;time>0;time--)
{
for(n=0;n<50;n++);
}
}
DS18B20温度采集程序如下:
voiddsreset(void)//18B20复位,初始化函数
{
inti;
TRISB=1;
ds=0;
i=103;
while(i>0)i--;
ds=1;
i=4;
while(i>0)i--;
}
chartempreadbit(void)//读1位函数
{
inti;
chardat;
TRISB=1;
ds=0;i++;//i++起延时作用
ds=1;i++;i++;
TRISB=3;
dat=ds;
i=8;while(i>0)i--;
return(dat);
}
chartempread(void)//读1个字节
{
chari,j,dat;
dat=0;
for(i=1;i<=8;i++)
{
j=tempreadbit();
dat=(j<<7)|(dat>>1);//读出的数据最低位在最前面,这样刚好一个字节在DAT里
}
return(dat);
}
voidtempwritebyte(chardat)//向18B20写一个字节数据
{
inti;
charj;
chartestb;
for(j=1;j<=8;j++)
{
testb=dat&0x01;
dat=dat>>1;
if(testb)//写1
{
TRISB=1;
ds=0;
i++;i++;
ds=1;
i=8;while(i>0)i--;
}
else
{
TRISB=1;
ds=0;//写0
i=8;while(i>0)i--;
ds=1;
i++;i++;
}
}
}
voidtempchange(void)//DS18B20开始获取温度并转换
{
dsreset();
delay_ms
(1);
tempwritebyte(0xcc);//写跳过读ROM指令
tempwritebyte(0x44);//写温度转换指令
}
intget_temp()//读取寄存器中存储的温度数据
{
chara,b;
dsreset();
delay_ms
(1);
tempwritebyte(0xcc);
tempwritebyte(0xbe);
a=tempread();//读低8位
b=tempread();//读高8位
temp=b;
temp<<=8;//两个字节组合为1个字
temp=temp|a;
f_temp=temp*0.0625;//温度在寄存器中为12位分辨率位0.0625°
temp=f_temp*10+0.5;//乘以10表示小数点后面只取1位,加0.5是四舍五入
f_temp=f_temp+0.05;
returntemp;//temp是整型
}
课程设计心得
参考文献
[1]郭天祥。
新概念51单片机C语言教程[M]2009.12
[1]孙安青。
PIC单片机使用C语言程序设计与典型实例[M]2008.06
附录:
源程序代码及注释
#include
#definepulsePORTBbits.RB0
#definedsPORTBbits.RB1
voiddelay_ms(unsignedinttime);
constunsignedchartable[10]={0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,0x7F,0x6F};
constunsignedchartable1[10]={0xBF,0x86,0xDB,0xCF,0xE6,0xED,0xFD,0x87,0xFF,0xEF};
constunsignedbit_set[4]={0xFE,0xFD,0xFB,0xF7};
voidtime1_rtc_init(void);
voidtimer1_rtc_isr(void);
voidInterruptHandlerHigh(void);
voiddisplay(inttime);
voiddisplay1(inttime);
voidmain(void);
intsecond,flag,fre,result,temp,count;
floatf_temp;
voiddsreset(void)//18B20复位,初始化函数
{
inti;
TRISB=0xf1;
ds=0;
i=103;
while(i>0)i--;
ds=1;
i=4;
while(i>0)i--;
}
chartempreadbit(void)//读1位函数
{
inti;
chardat;
TRISB=0xf1;
ds=0;i++;//i++起延时作用
ds=1;i++;i++;
TRISB=0xf3;
dat=ds;
i=8;while(i>0)i--;
return(dat);
}
chartempread(void)//读1个字节
{
chari,j,dat;
dat=0;
for(i=1;i<=8;i++)
{
j=tempreadbit();
dat=(j<<7)|(dat>>1);//读出的数据最低位在最前面,这样刚好一个字节在DAT里
}
return(dat);
}
voidtempwritebyte(chardat)//向18B20写一个字节数据
{
inti;
charj;
chartestb;
for(j=1;j<=8;j++)
{
testb=dat&0x01;
dat=dat>>1;
if(testb)//写1
{
TRISB=0xf1;
ds=0;
i++;i++;
ds=1;
i=8;while(i>0)i--;
}
else
{
TRISB=0xf1;
ds=0;//写0
i=8;while(i>0)i--;
ds=1;
i++;i++;
}
}
}
voidtempchange(void)//DS18B20开始获取温度并转换
{
dsreset();
delay_ms
(1);
tempwritebyte(0xcc);//写跳过读ROM指令
tempwritebyte(0x44);//写温度转换指令
}
intget_temp()//读取寄存器中存储的温度数据
{
chara,b;
dsreset();
delay_ms
(1);
tempwritebyte(0xcc);
tempwritebyte(0xbe);
a=tempread();//读低8位
b=tempread();//读高8位
temp=b;
temp<<=8;//两个字节组合为1个字
temp=temp|a;
f_temp=temp*0.0625;//温度在寄存器中为12位分辨率位0.0625°
temp=f_temp*10+0.5;//乘以10表示小数点后面只取1位,加0.5是四舍五入
f_temp=f_temp+0.05;
returntemp;//temp是整型
}
voidmain(void)
{
second=0;
TRISC=0;/*configurePORTDforoutput*/
TRISD=0;
TRISB=0xf1;
time1_rtc_init();
flag=0;
fre=0;
result=0;
count=0;
while
(1)
{
/*if(flag==1&&pulse==1)
{
fre+=2;
flag=0;
}
elseif(pulse==0&&flag==0)
{
flag=1;
}*/
if(result!
=1)
display(second);
else
{
while
(1)
{
tempchange();
temp=get_temp();//采集温度
count++;
if(count==201)count=0;
if(count<=100)
{
display(fre);
}
elseif(count<=200)
{
display1(temp);
}
}
}
}
}
voiddisplay(inttime)
{
PORTC=table[time%10];
PORTD=bit_set[3];
delay_ms(10);
PORTC=table[(time/10)%10];
PORTD=bit_set[2];
delay_ms(10);
PORTC=table[time/100];
PORTD=bit_set[1];
delay_ms(10);
}
voiddisplay1(inttime)
{
PORTC=table[time%10];
PORTD=bit_set[3];
delay_ms(10);
PORTC=table1[(time/10)%10];
PORTD=bit_set[2];
delay_ms(10);
PORTC=table[(time)/100];
PORTD=bit_set[1];
delay_ms(10);
}
voidtime1_rtc_init(void)
{
INTCON=0x20;//disableglobalandenableTMR0interrupt
INTCON2=0x84;//TMR0highpriority
RCONbits.IPEN=1;//enableprioritylevels
TMR0H=100;//cleartimer
TMR0L=0;//cleartimer
T0CON=0x85;//setuptimer0-prescaler1:
8
INTCONbits.GIEH=1;//enableinterrupts
INTCONbits.INT0IF=0;
IN