资源描述
基于单片机自行车风火轮设计及制作
摘要
本课题研究对象是用单片机控制安装在自行车车轮辐条上led动态显示,使其能呈现出各种有趣风火轮发光图像。这会让我们自行车在夜晚更加炫目有个性,而且提高夜晚骑车安全性。电路系统以avr单片机为核心,霍尔开关产生电平为信号源,测算出车轮转动一圈所需时间,从而分时段控制led发亮。本文首先介绍本系统所需要两个芯片atmega8和74hc595,阐述了其功能结构及其应用。然后介绍本设计总体方案并附上基本原理图,并且对单片机和接口设计和各自工作原理进行详细说明。最后谈到该系统软件设计并附上程序。
关键词:风火轮,霍尔开关,74HC595,单片机
Design of Hot Wheels based on Avr MCU
Abstract
The object of this research is SCM so that it led to a dynamic display showing a variety of common images, its application will enable us to more of a bike at night there are dazzling personality, but also to improve the safety of night riding. The system is single-chip microcomputer as the core avr Hall switch for the signal source of the response, measured around the time required for the rotation of the wheels, which led at times to control the display. This paper first introduces the system required two chips atmega8 and 74hc595, described the function of its structure and its application. And then introduce the design of the overall program with the basic principles of map, and single-chip microcomputer and interface design and principle of their work in detail. Finally, on the system with the software design process.
Keyword: feng huo lun ,Hall switch , 74hc595 ,scm
目录
摘要························································1
英文摘要····················································1
第一章 绪论·················································3
1.1 本课题目及研究意义······························· 3
1.2 本课题应解决主要问题······························3
1.3 本章小结··············································3
第二章 风火轮系统概述·······································4
2.1 风火轮系统功能需求····································4
2.2 风火轮结构设计·········································4
2.3 本章小结························4
第三章 系统模块设计······················5
3.1 主要元器件介绍··········································5
3.1.1 atmega8: avr单片机···································5
3.1.2 74hc595: 32位串行led显示驱动器······················6
3.2 各模块组成设计······················7
3.2.1感应电路设计··········································8
3.2.2 信号处理电路·········································8
3.2.3 32位led驱动模块····································8
第三章 软件设计···············································9
第一章 绪论
1.1 本课题目及研究意义
数字电路产品在生活中有着极其广泛应用,包括计算机、数字通信、智能仪器仪表、自动控制及航天等领域。这些给人们生活,工作等方面带来了极大方便。
风火轮是一种非常有用创新设计,我国是自行车大国,漆黑夜晚我们骑车往往不是很安全,后方行人往往不太容易察觉,但这项设计很大解决了这个问题,有了它夜晚我们自行车会发出亮光,会让别行人注意,从而减少事故。并且风火轮绚丽图案,会使我们生活更有乐趣。
本课题包含了感应电路,数码管驱动电路,单片机程序下载电路,控制电路等四个部分设计。通过对四个部分设计,要求实现风火轮基本功能。其中单片机中集成了定时,中断电路。
此次研究旨在对自己专业知识掌握程度进行检验,加强解决电子方面常见实际问题能力,掌握一般电子电路设计方法及设计步骤,积累实际电子制作经验,实现向更复杂更实用应用领域过渡。目在于巩固基础、注重设计、培养技能、追求创新、走向实用。
1.2 本课题应解决主要问题
本课题研究通过单片机等集成电路实现led动态显示。在设计过程中需要解决主要问题有:
第一:如何让LED在特定时间点亮,从而组成图案
第二:图像点阵取样
第三:不需要使用时,风火轮如何休眠。
1.3 本章小结
本章说明了课题研究意义、研究目、应解决主要问题等各方面内容。从宏观角度对本次毕业设计背景、目、内容、思路等进行了阐述。
第二章 风火轮系统概述
2.1风火轮系统功能需求
本课题研究对象是led动态显示系统,该系统以avr单片机为核心,通过读取霍尔开关捕捉车轮每转一周电平跳变,用timer0计算出这个时间。用这个时间 1/256 做为每条显示射线持续时间,由timer1控制输出。再经74hc595,从而驱动数码管。其大致结构图如下:
2.2 风火轮结构设计
车轮转动感应电路
信号处理电路
发光二极管驱动电路
显示装置电路
处理器程序下载,电源控制电路
风火轮结构框图
将系统功能需求结构化后,不难发现,整体设计思路及方向更加明确,整个系统主要可划分为三个模块:
(1)感应模块---进行车轮转圈所需时间测定,并转成电信号给信号处理器
(2)信号处理模块--- 包含定时计数器,外部中断电路,休眠模式
(3)LED驱动模块---接收处理器传来信号,驱动串联LED
2.3 本章小结
本章主要阐述了风火轮基本工作原理和系统功能需求,并对系统结构进行了阐述。在说明系统功能需求过程中,详细叙述了系统所需实现基本功能,使得整个设计清晰明了。
第三章 系统模块设计
3.1 芯片介绍
3.1.1 atmega8: avr单片机
Atmega8 是atmel公司在2002年第一季度推出一款新型avr高档单片机。芯片内部集成了较大容量存储器和丰富强大硬件接口电路,采用小引脚封装(本系统采用是MLF32),相比先前单片机,有着更多接口,更好省电性,抗干扰性和稳定性,而且价格便宜,在应用市场极具竞争力。
主要性能如下:
●高性能、低功耗8位avr微控制器,先进RISC精简指令集结构
●较大容量非易失性程序和数据存储器以及存储器
●强大外部接口性能
●特殊微控制器性能
●I/O口和封装(32脚mlf封装)
●宽工作电压(4.5V)
●高运行速度(0~8MHZ)
●低功耗(4MHZ,3V, 25)
1.1.2 管脚及内部结构
1.1.3 管脚封装参见图1
1.1.4 内部结构参见图2
(图1)Atmega8芯片引脚图
(图2)Atmega8单片机系统结构图
Atmega8外部管脚定义如下:
VCC电源正(数字):4.5V
GND 电源地
信号处理模块主要部分
3.1.2 74hc595: 32位串行led显示驱动器
74hc595特点如下:
●8位串行输入
●8位串行或并行输出
●存储状态寄存器,三种状态
●输出寄存器可以直接清除
●100MHz移位频率
●输出能力:
●并行输出,总线驱动
●串行输出;标准
●中等规模集成电路
●串行到并行数据转换
74hc595引脚图
表 74hc595引脚功能
符号
引脚
描述
Q0…Q7
15,1,2,3,4,5,6,7
并行数据输出
GND
8
地
Q7’
9
串行数据输出
MR
10
主复位(低电平)
SHCP
11
移位寄存器时钟输入
STCP
12
存储寄存器时钟输入
OE
13
输出有效(低电平)
DS
14
串行数据输入
VCC
16
电源
3.2 各模块组成设计
3.2.1感应电路设计
感应电路是整个系统信号源,我选用是霍尔开关,车轮每转一圈,就会产生一个下降沿沿波形,由此波形处理器判断时间。
3.2.2 信号处理电路
程序下载时,AVR处于SPI从机方式,接口总线时钟SCK,MOSI为从机数据输入,MOSO为从机数据为输出。PB6系统复位引脚,TXD为USART总线数据输出口,RXD为USART总线数据输出口。AVR为主机方式时,MOS0为主机数据输入。
单片机有两个外部中断INTO,INT1,INT0用于按键检测,长按键大于3s,系统即处于休眠状态,INT1霍尔传感器触发(下降沿)。
还用到了Atmega8内部集成定时器计数器T0,T/C1. T0所选时钟经256分频,一旦TCNT0计数值及OCRA1数据相等,T/C1中断。促发LED驱动模块。
3.2.3 32位led驱动模块
74HC595端口9串接下一595SER端口,公用CLK,RCLK。四片595串接组成32LED驱动模块。
3.3 本章小结
本章介绍了抢答器中使用到主要元器件管脚图、功能表,着重介绍了三个模块(感应电炉、信号处理、驱动电路)设计和工作过程,使得整个风火轮系设计理念和工作过程很清晰呈现了出来。
风火轮原理图
第三章 软件设计
编译软件WINAVR ,经编译获得 hex文件,PROGISP烧录FLASH
编译程序如下:
#include <avr/io.h>
#include <avr/interrupt.h>
#include <avr/wdt.h>
#include <avr/sleep.h>
#include <avr/pgmspace.h>
#include <avr/eeprom.h>
#include <util/delay.h>
/*----------------*
* 主时钟 *
*----------------*/
#ifndef F_CPU
#define F_CPU 8000000 // 8MHz
#endif
/*----------------*
* 宏定义 *
*----------------*/
#define NUM_LEDS 32 // 单面LED数据
#define NUM_PIXELS 256 // 像素数256 (刚好一个字节)
#define PIC_MODE 1 // 图像模式 1:数据存在FLASH
// 1/4:数据存在EE 512byte
#define HALL_DEBOUNCE 4 // 400us
#define STANDBY_TIMEOUT 50000 // 50000×100us = 5s
#define BUTTON_DEBOUNCE 10 // 100ms
#define POWEROFF_TIMEOUT 200 // 约3s
/*----------------*
* 按键入口 *
*----------------*/
#define KEY_PRESED !(PIND&_BV(PD2))
/*----------------*
*霍尔传感电源控制*
*----------------*/
#define HALL_ON PORTD|= _BV(PD6)
#define HALL_OFF PORTD&=~_BV(PD6)
/*----------------*
* 74HC595引脚 *
*----------------*/
#define SET_SER PORTB|= _BV(PB4) // 数据------74HC595 14#
#define CLR_SER PORTB&=~_BV(PB4)
#define SET_SCLK PORTB|= _BV(PB5) // 移位时钟--74HC595 11#
#define CLR_SCLK PORTB&=~_BV(PB5)
#define SET_RCLK PORTD|= _BV(PD4) // 移位时钟--74HC595 11#
#define CLR_RCLK PORTD&=~_BV(PD4)
/*----------------*
* 变量定义 *
*----------------*/
unsigned char tHall; // 霍尔传感器检测时间
unsigned int tLap; // 轮子转一圈所用时间存放变量
unsigned long leds; // LED对应缓存
unsigned int offset; // 数据读取索引
#if PIC_MODE == 1
const unsigned char pic[NUM_PIXELS*PIC_MODE*4]; // flash图像数据
#endif
/*----------------*
* 函数声名 *
*----------------*/
void ctrl595_out(unsigned long );
/*----------------------------------------------*
* 端口初始化 *
*----------------------------------------------*/
void port_init(void)
{
PORTB = 0xFF;
DDRB = 0x38;
PORTC = 0x7F; //m103 output only
DDRC = 0x00;
PORTD = 0xBF;
DDRD = 0x52;
}
/*----------------------------------------------*
* T0设置 *
* ------------------------------------ *
* TIMER0 initialize - prescale:256 *
* WGM: Normal *
* desired value: 100uSec *
* actual value: 96.000uSec (4.0%) *
*----------------------------------------------*/
void timer0_init(void)
{
TCCR0 = 0x00; // stop
TCNT0 = 0x00; // set count
TCCR0 = 0x04; // start timer
}
/*----------------------------------------------*
* T/C1设置 *
* ------------------------------------ *
* TIMER1 initialize - prescale:1 *
* WGM: 4) CTC, TOP=OCRnA *
* desired value: 100uSec *
* actual value: 99.962uSec (0.0%) *
*----------------------------------------------*/
void timer1_init(void)
{
TCCR1B = 0x00; // stop
TCNT1H = 0x00 /*INVALID SETTING*/; //setup
TCNT1L = 0x00 /*INVALID SETTING*/;
OCR1AH = 0x00 /*INVALID SETTING*/;
OCR1AL = 0x00 /*INVALID SETTING*/;
OCR1BH = 0x00 /*INVALID SETTING*/;
OCR1BL = 0x00 /*INVALID SETTING*/;
ICR1H = 0x00 /*INVALID SETTING*/;
ICR1L = 0x00 /*INVALID SETTING*/;
TCCR1A = 0x00;
TCCR1B = 0x00; // stop Timer
}
/*----------------------------------------------*
* T0 100u定时中断 *
*----------------------------------------------*/
SIGNAL (TIMER0_OVF_vect)
{
TCNT0 = 0x00; // reload counter value
if (tHall != 0xff)
tHall++;
if (tLap != 0xffff)
tLap++;
}
/*----------------------------------------------*
* T/C1 CTC(比较匹配时清零定时器)模式 *
* ------------------------------------ *
* 数器数值TCNT0一直累加到TCNT0及OCR0A匹配,然后 *
* TCNT0 清零.产生此中断 *
*----------------------------------------------*/
SIGNAL (TIMER1_COMPA_vect)
{
if (tLap < STANDBY_TIMEOUT) // 转一圈地时间小于5S才显示
{
#if PIC_MODE == 1
leds=((long)pgm_read_byte(pic+offset+3)<<24)|((long)pgm_read_byte(pic+offset+2)<<16)
|((long)pgm_read_byte(pic+offset+1)<< 8)| pgm_read_byte(pic+offset+0);
#else
eeprom_read_block(&leds,(void *)(offset % (NUM_PIXELS*PIC_MODE*4)),sizeof(leds));
#endif
ctrl595_out(leds); // 将显示数据送出
/* 关中断,确保在同一时间其它中断打断写入此地址 */
cli();
if(offset<(NUM_PIXELS*PIC_MODE*4-4))
offset += 4; // 地址指针移向下一数据区
else
{
ctrl595_out(1); // turn off all but one LED;
}
sei();
}
else // 转一圈超过5S
{
cli();
TCCR1B = 0x00; // 停止T/C1
sei();
ctrl595_out(1); // turn off all but one LED;
}
}
/*----------------------------------------------*
* 外部中断0:按键检测(低电平) *
*----------------------------------------------*/
SIGNAL (INT0_vect)
{
unsigned char tKey=0;
while (KEY_PRESED) // 等待释放按键
{
wdt_reset();
_delay_ms(10); // 10ms
if (++tKey>250)
tKey = 250;
}
if (tKey > BUTTON_DEBOUNCE) // 100ms
{
if (tKey < POWEROFF_TIMEOUT)// 约3s
{
WDTCR = _BV(WDE);
while (1); // 狗死循环造成复位,激活系统
}
else // 长按键休眠待机
tLap = 0xffff;
}
}
/*----------------------------------------------*
* 外部中断1:霍尔传感器触发(下降沿) *
*----------------------------------------------*/
SIGNAL (INT1_vect)
{
cli();
if (tHall > HALL_DEBOUNCE) // 软抗骚扰,防止误触发
{
/* 我们知道最后一次霍尔传感器触发后毫秒数,
以及每次扫描有256条射线状“像素” 以便分别在
每个像素间断期间取得必要毫秒数,现在仅仅使
得定时器1处于那个比率,也就是T/C1中断时间是
T0256之1,T0所选时钟256分频,则T/C1所选时
时钟不分频*/
TCNT1H = 0x00;
TCNT1L = 0x00; // timer1计数值清0
if ((tLap < 0xff) && (tLap > 0x3)) // 时间太短太长都不处理
{
OCR1AH = tLap;
OCR1AL = TCNT0; // 输出比较寄存器赋值
TCNT0 = 0; // T0计数值清零
#if PIC_MODE == 1
offset = 0;
#else
offset = 1; // 取出源数据存放地址,EE地址0空出未用
#endif
TCCR1B = 0x09; // 开始T/C1
}
else
{
ctrl595_out(1);
TCCR1B = 0x00; // 停止T/C1
}
tLap = 0;
}
else
{
ctrl595_out(1);
}
tHall = 0;
sei();
}
/*----------------------------------------------*
* 595输出控制 *
*----------------------------------------------*/
void ctrl595_out(unsigned long dat)
{
unsigned char i;
for (i=0;i<NUM_LEDS;i++)
{
CLR_SCLK; // 移位时钟置低
if (dat&1)
CLR_SER; // 置高数据时钟
else
SET_SER; // 接低数据时钟
dat>>=1;
// __
SET_SCLK; // __↑ 移位时钟上升沿,数据进入移位寄存器
}
CLR_RCLK;
asm("nop"); asm("nop");
asm("nop"); asm("nop"); // __
SET_RCLK; // __↑ 锁存电平上升沿,数据输出到并行端口
}
/*----------------------------------------------*
* 初始化配置 *
*----------------------------------------------*/
void init_devices(void)
{
cli(); //disable all interrupts
port_init();
wdt_enable(WDTO_500MS);
timer0_init();
timer1_init();
MCUCR = 0x08; INT0低电平产生中断请求
GICR = 0xC0; INT1下降沿产生一个中断请求
TIMSK = 0x11; //timer interrupt sources 执行T/C0溢出中断请求
sei(); //re-enable interrupts
}
/*----------------------------------------------*
* 主程序 *
*----------------------------------------------*/
int main(void)
{
init_devices();
#if PIC_MODE == 1
offset = 0;
#else
offset = 1; // EE地址0空出未用
#endif
tLap = 0;
tHall = 0xff;
HALL_ON; // 打开霍尔传感器
leds=1;
ctrl595_out(1);
while(1)
{
wdt_reset();
if (tLap == 0xffff)
{
cli();
/* 关闭有LED及霍尔传感器 */
HALL_OFF;
ctrl595_out(0);
/* 关闭看门狗 */
wdt_disable();
/* 休眠待机
sleep.h里面定义常数,对应各种睡眠模式
#define SLEEP_MODE_IDLE 0 空闲模式
#define SLEEP_MODE_ADC _BV(SM0) ADC 噪声抑制模式
#define SLEEP_MODE_PWR_DOWN _BV(SM1) 掉电模式
#define SLEEP_MODE_PWR_SAVE (_BV(SM0)|_BV(SM1)) 省电模式
#define SLEEP_MODE_STANDBY (_BV(SM1)|_BV(SM2)) Standby 模式
#define SLEEP_MODE_EXT_STANDBY (_BV(SM0)|_BV(SM1)|_BV(SM2))扩展Standby模式
void set_sleep_mode (uint8_t mode); 设定睡眠模式
void sleep_mode (void); 进入睡眠状态
sleep_enable();
set_sleep_mode(SLEEP_MODE_PWR_SAVE); // 省电模式
sei();
sleep_cpu();
}
}
}
结束语:
本系统是基于AVR单片机设计led动态显示系统,采用美国atmel公司新近推出一种新型高速单片机,接口电路简单,可靠,再外接数码管等组成功能强大检测及显示系统。在我国这么一个自行车众多国家,在将来肯定具有广阔前景。
参考文献:
[1] 康华光 主编, 电子技术基础(数字部分),北京:高等教育出版社,2005年
[2] 康华光 编著, 电子技术基础(模拟部分),北京:高等教育出版社,2005年
[3]马潮等 ATMEGA8原理急用手册
[4] ouravr网站上一些参考资料
[5]刘汧 CodeVisionAVR C 库函数介绍
[6]沈文 AVR单片机 C语言开发入门指导
30 / 30
展开阅读全文