1  系统方案设计

系统整体设计

电子智能补光器的设计思路:首先通过单片机判断特殊天气模式是否启用,如果启用则直接亮黄灯并在手机上显示出来。确定特殊天气模式没有启用时,通过季节模块判断当前月份对应的季节来确定补光模式。通过光照传感器将外界光照强度与对应季节设定光照阈值进行比较,当外界光照强度大于设定阈值时进行补光操作,并通过蓝牙连接在手机上显示当前补光模式以及光照强度。

1.2 设计任务

主要任务简述:以单片机为核心,设计电子智能补光器,以满足各种不同情境下对光照需求的差异。

要求简述:

(1)在外界光照强度大于所设定阈值时补光器保持不工作状态,光照强度小于设定阈值时开始补光;

(2)可选择春、夏、秋、冬四种模式,分别对应四种不同的阈值电压;

(3)设置特殊天气模式,开启特殊天气模式后亮起黄色雾灯;

(4)通过蓝牙连接手机,显示当前的模式和光照强度。

1.3 模块方案选型

1.3.1主控方案选型

STC89C52单片机是宏晶科技推出的高反应速度、低功率消耗、有着很强抵的挡外界干扰能力的单片机,而且该单片机的指令代码非常切合传统的8051单片机,并且与传统51单片机对比而言,该单片机速度更快,是传统51单片机的8~12倍。除此之外,该单片机还有6时钟周期和12时钟周期可以任意选择。

主要特性如下:

(1)新一代8051单片机,6时钟机器周期和12时钟机器周期可以任意选择,指令代码非常契合传统8051单片机。

(2)工作电压:5.5V~3.3V(5V单片机)。

(3)工作频率范围处于0~40MHz之间,相当于普通8051单片机工作频率的0~80MHz范围,而且新一代单片机的实际工作频率可达48MHz。

(4)一共具有3个16位定时器,也就是定时器T0、T1、T2。

(5)外部中断4路,低电平触发或下降沿中断电路,PowerDown模式可通过外部中断低电平触发中断的方式触发。

1.3.2光电转换器的选择

ADC0832是NS(National Semiconductor)公司生产的串行接口8位A/D转换器,通过三线接口与单片机连接,功耗低,性能价格比较高,合适使用在袖珍式的智能仪器仪表中。ADC0832为8位分辨率A/D转换芯片,其最高分辨可达256级,可以适应一般的模拟量转换要求。芯片具有双数据输出可作为数据校验,以减少数据误差,转换速度快且稳定性能强。独立的芯片使能输入,使多器件连接和处理器控制变得更加方便。通过DI 数据输入端,可以轻易的实现通道功能的选择。其主要特点如下:

(1)8位分辨率,其最高分辨可达256级;

(2)双通道A/D转换;

第3页 共50页

(3)电源供电时光电转换器的输入电压在0~5V之间;

选择该A/D转换芯片,不仅因为其体积小、功耗低,而且可以适应一般的模拟量转换要求,完全满足系统的要求。另外,其内部电源输入与参考电压的复用,使得转换芯片的模拟电压输入在0~5V之间,电源电路供电可以同时满足51单片机和该芯片的共同使用。除此之外该芯片的转换时间极短,仅为32μS,反应非常迅速,另外该芯片具有双数据输出可作为数据校验的工具,以此来减少实验数据误差,转换速度快并且稳定性能出色。单独工作的芯片的使能输入,可以更轻松地对多元件进行连接,同时也可以更加方便地控制处理器。通过DI 数据输入端,使得实现通道功能的选择变的易如反掌。除此之外,价格上的优势同样也是选择它的原因之一。

1.3.3显示器的选择

LCD1602液晶显示器是广泛使用的一种工业字符型液晶显示模块。由字符型液晶显示器(LCD)、控制驱动主电路HD44780及其扩展驱动电路HD44100,以及少量电阻、电容元件和结构件等装配在PCB板上而组成,能够同时显示16x02即32个字符。(16列2行)。但寄存器不止32个,有一些显示效果,如字符一个个显示、字符从左到右或从右到左显示等等,显示效果简单。当然也有其他更好的选择,例如12864液晶显示器,它的显示模块是128×64点阵的汉字图形型液晶显示模块,可显示汉字及图形,具有多种功能:光标显示、画面移位、睡眠模式等。

其实综合来说,二者编程方面的难度差不多,原理方面也差不多,甚至12864液晶显示器更胜一筹,因为该显示器显示更全面,字符也更多,需要进行更多操作的话自然是12864液晶显示器能够胜任。但是对比来说的话,1602液晶显示器也能实现设计的要求,而且相对来说更重要的原因就是1602液晶显示器比较廉价,网上购买也比较便宜,最低五六块钱左右。而12864液晶显示器网上购买最便宜的也要在二三十左右。所以从造价方面以及使用方面考虑,当然是价格低廉而且功能也不欠缺的优先。因此选择1602液晶显示器作为显示器件。

2  硬件设计

2.1 单片机模块

单片机的主要特点有:

(1)有出色的性能单价比,高效能、低电压,易于制作便携式产品。

(2)集成度高,体积小,有较高的稳定性。而且单片机把各功能零件组合在一块芯片上,内部结构使用的是总线结构,不仅减轻了各芯片彼此之间的连线,还大大增加了单片机的安全性和抗干扰能力。

(3)控制功能强。为求满足工业控制的要求,通常单片机的指令系统中均

第4页 共50页

有极多样的转移指令、I/O口的逻辑操作和位处理特性。单片机的逻辑控制功能及运转速度均远高于同一等级的微机。

(4)外部总线增加了I2C(Inter-Integrated Circuit)及SPI(Serial Peripheral Interface)等串行总线方式,逐步缩小了体积,精简了构造。单片机的系统扩展、系统配置较典型、规范,容易构成各种规模的应用系统。

PORT0(P0.0~P0.7):端口0是一个8位宽的开路汲极双向输出入端口,共有8个位,P0.0表示位0,P0.1表示位1,依此类推。其他三个I/O端口(P1、P2、P3)则不具有此电路组态,而是内部有一提升电路,P0在当做I/O用时可以推动8个LS的TTL负载。

PORT1(P1.0~P1.7):端口1也是具有内部提升电路的双向I/O端口,其输出缓冲器可以推动4个LSTTL负载,同样地若将端口1的输出设为高电平,便是由此端口来输入数据。

PORT2(P2.0~P2.7):端口2是具有内部提升电路的双向I/O端口,每一个引脚可以推动4个LS的TTL负载,若将端口2的输出设为高电平时,此端口便能当成输入端口来使用。P2除了当做一般I/O端口使用外,若是在STC89C52扩充外接程序存储器或数据存储器时,也提供地址总线的高字节A8~A15,这个时候P2便不能当做I/O来使用了。

PORT3(P3.0~P3.7):端口3也具有内部提升电路的双向I/O端口,其输出缓冲器可以推动4个TTL负载,同时还多工具有其他的额外特殊功能,包括串行通信、外部中断控制、计时计数控制及外部数据存储器内容的读取或写入控制等功能。单片机的引脚图如图3-1所示。

#include "51Lib_Configure.h"

#include "51Lib_Declaration.h"

#if _CONFIG_FUNC_LCD1602_ == CH_ENABLE

#define _NOP() _nop_()

#define DataPort P0

#define DataPIN P0

#define CLR_RS (lcd1602_RS=0)

#define SET_RS (lcd1602_RS=1)

#define CLR_RW (lcd1602_RW=0)

#define SET_RW (lcd1602_RW=1)

#define CLR_EN (lcd1602_EN=0)

#define SET_EN (lcd1602_EN=1)

/*

LcdReset(); //LCD1602初始化

DelayMs(10);

sprintf(temp,"1111111111111111");//更新显示

DispStr(0,0,(unsigned char *)temp);//打印显示

sprintf(temp,"1111111111111111");//更新显示

DispStr(0,1,(unsigned char *)temp);//打印显示

*/

/***********************************************

函数名称:DispNum

功 能:让液晶从某个位置起连续显示一个数值,前面不会补0

参 数:x--位置的列坐标

y--位置的行坐标

Dis_dat--需要显示的数

Dis_Len--需要显示的宽度

返回值 :无

***********************************************/

void DispNum(uchar x, uchar y, uint Dis_dat, uchar Dis_Len)

{

uchar i;

uint dat = 1;

Disp1Char(x+Dis_Len-1,y,Dis_dat%10+0x30);

if(Dis_Len == 1)

return;

for(i = 1;i < Dis_Len;i++)

dat*=10;

for(i = 1; i < Dis_Len ; i++)

{

//dat = pow(10, Dis_Len-i);

if(Dis_dat >= dat)

Disp1Char(x+i-1,y,Dis_dat/dat%10+0x30);

else

Disp1Char(x+i-1,y,' ');

dat/=10;

}

}

/***********************************************

函数名称:DispStr

功 能:让液晶从某个位置起连续显示一个字符串

参 数:x--位置的列坐标

y--位置的行坐标

ptr--指向字符串存放位置的指针

返回值 :无

***********************************************/

void DispStr(uchar x,uchar y,uchar *ptr)

{

uchar *temp;

uchar i,n = 0;

temp = ptr;

while(*ptr++ != '\0') n++; //计算字符串有效字符的个数

for (i=0;i

{

Disp1Char(x++,y,temp[i]);

if (x == 0x10)

{

break;

}

}

}

/*******************************************

函数名称:DispNchar

功 能:让液晶从某个位置起连续显示N个字符

参 数:x--位置的列坐标

y--位置的行坐标

n--字符个数

ptr--指向字符存放位置的指针

返回值 :无

*******************************************

void DispNChar(uchar x,uchar y, uchar n,uchar *ptr)

{

uchar i;

for (i=0;i

{

Disp1Char(x++,y,ptr[i]);

if (x == 0x10)

{

x = 0;

y ^= 1;

}

}

}

*/

/*******************************************

函数名称:LocateXY

功 能:向液晶输入显示字符位置的坐标信息

参 数:x--位置的列坐标

y--位置的行坐标

返回值 :无

********************************************/

void LocateXY(uchar x,uchar y)

{

uchar temp;

temp = x&0x0f;

y &= 0x01;

if(y) temp |= 0x40; //如果在第2行

temp |= 0x80;

LcdWriteCommand(temp,1);

}

/*******************************************

函数名称:Disp1Char

功 能:在某个位置显示一个字符

参 数:x--位置的列坐标

y--位置的行坐标

data--显示的字符数据

返回值 :无

********************************************/

void Disp1Char(uchar x,uchar y,uchar data1)

{

LocateXY( x, y );

LcdWriteData( data1 );

}

/*******************************************

函数名称:LcdReset

功 能:对1602液晶模块进行复位操作

参 数:无

返回值 :无

********************************************/

void LcdReset(void)

{

// DataDir = 0xFF; //数据端口设为输出状态

LcdWriteCommand(0x38, 0); //规定的复位操作

DelayMs(5);

LcdWriteCommand(0x38, 0);

DelayMs(5);

LcdWriteCommand(0x38, 0);

DelayMs(5);

LcdWriteCommand(0x38, 1); //显示模式设置

LcdWriteCommand(0x08, 1); //显示关闭

LcdWriteCommand(0x01, 1); //显示清屏

LcdWriteCommand(0x06, 1); //写字符时整体不移动

LcdWriteCommand(0x0c, 1); //显示开,不开游标,不闪烁

}

/*------------------------------------------------

清屏函数

------------------------------------------------*/

void LcdClear(void)

{

LcdWriteCommand(0x01,1);

DelayMs(5);

}

/*******************************************

函数名称:LcdWriteCommand

功 能:向液晶模块写入命令

参 数:cmd--命令,

chk--是否判忙的标志,1:判忙,0:不判

返回值 :无

********************************************/

void LcdWriteCommand(uchar cmd,uchar chk)

{

if (chk) WaitForEnable(); // 检测忙信号?

CLR_RS;

CLR_RW;

_NOP();

DataPort = cmd; //将命令字写入数据端口

_NOP();

SET_EN; //产生使能脉冲信号

_NOP();

_NOP();

CLR_EN;

}

/*******************************************

函数名称:LcdWriteData

功 能:向液晶显示的当前地址写入显示数据

参 数:data--显示字符数据

返回值 :无

********************************************/

void LcdWriteData( uchar data1 )

{

WaitForEnable(); //等待液晶不忙

SET_RS;

CLR_RW;

SET_EN;

_NOP();

DataPort = data1; //将显示数据写入数据端口

_NOP();

//产生使能脉冲信号

_NOP();

_NOP();

CLR_EN;

}

/*******************************************

函数名称:WaitForEnable

功 能:等待1602液晶完成内部操作

参 数:无

返回值 :无

********************************************/

void WaitForEnable(void)

{

unsigned int later=0;

DataPort=0xff;

CLR_RS;

SET_RW;

_NOP();

SET_EN;

_NOP();

_NOP();

// while((DataPIN&Busy)!=0);

while(((DataPIN&0x80)!=0)&&(later<1000)) //检测忙标志

{

DelayUs2x(2);

later++;

}

CLR_EN;

// DataDir|=0xFF; //将P4口切换为输出状态

}

#endif

相关文章

评论可见,请评论后查看内容,谢谢!!!
 您阅读本篇文章共花了: